@webex/plugin-authorization-browser-first-party 3.0.0-beta.9 → 3.0.0-bnr.2
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/dist/authorization.js +8 -75
- package/dist/authorization.js.map +1 -1
- package/dist/config.js +0 -3
- package/dist/config.js.map +1 -1
- package/dist/index.js +1 -8
- package/dist/index.js.map +1 -1
- package/dist/plugin-authorization-browser-first-party.d.ts +21 -0
- package/dist/tsdoc-metadata.json +11 -0
- package/dist/types/authorization.d.ts +12 -0
- package/dist/types/config.d.ts +7 -0
- package/dist/types/index.d.ts +2 -0
- package/package.json +10 -10
- package/src/authorization.js +33 -36
- package/src/config.js +18 -17
- package/src/index.js +2 -5
- package/test/automation/fixtures/app.js +15 -15
- package/test/automation/fixtures/index.html +18 -15
- package/test/automation/spec/authorization-code-grant.js +86 -68
- package/test/unit/spec/authorization.js +177 -155
|
@@ -19,28 +19,28 @@ import Authorization from '@webex/plugin-authorization-browser-first-party';
|
|
|
19
19
|
// Necessary to require lodash this way in order to stub the method
|
|
20
20
|
const lodash = require('lodash');
|
|
21
21
|
|
|
22
|
-
|
|
23
22
|
browserOnly(describe)('plugin-authorization-browser-first-party', () => {
|
|
24
23
|
describe('Authorization', () => {
|
|
25
|
-
function makeWebex(
|
|
24
|
+
function makeWebex(
|
|
25
|
+
href = 'https://example.com',
|
|
26
|
+
csrfToken = undefined,
|
|
27
|
+
pkceVerifier = undefined,
|
|
28
|
+
config = {}
|
|
29
|
+
) {
|
|
26
30
|
const mockWindow = {
|
|
27
31
|
history: {
|
|
28
32
|
replaceState(a, b, location) {
|
|
29
33
|
mockWindow.location.href = location;
|
|
30
|
-
}
|
|
34
|
+
},
|
|
31
35
|
},
|
|
32
36
|
location: {
|
|
33
|
-
href
|
|
37
|
+
href,
|
|
34
38
|
},
|
|
35
39
|
sessionStorage: {
|
|
36
|
-
getItem: sinon.stub()
|
|
37
|
-
.onCall(0)
|
|
38
|
-
.returns(pkceVerifier)
|
|
39
|
-
.onCall(1)
|
|
40
|
-
.returns(csrfToken),
|
|
40
|
+
getItem: sinon.stub().onCall(0).returns(pkceVerifier).onCall(1).returns(csrfToken),
|
|
41
41
|
removeItem: sinon.spy(),
|
|
42
|
-
setItem: sinon.spy()
|
|
43
|
-
}
|
|
42
|
+
setItem: sinon.spy(),
|
|
43
|
+
},
|
|
44
44
|
};
|
|
45
45
|
|
|
46
46
|
sinon.spy(mockWindow.history, 'replaceState');
|
|
@@ -49,37 +49,52 @@ browserOnly(describe)('plugin-authorization-browser-first-party', () => {
|
|
|
49
49
|
children: {
|
|
50
50
|
authorization: Authorization,
|
|
51
51
|
credentials: Credentials,
|
|
52
|
-
services: Services
|
|
52
|
+
services: Services,
|
|
53
53
|
},
|
|
54
|
-
request: sinon
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
54
|
+
request: sinon
|
|
55
|
+
.stub()
|
|
56
|
+
.returns(
|
|
57
|
+
Promise.resolve({body: {access_token: 'AT', token_type: 'Fake', refresh_token: 'RT'}})
|
|
58
|
+
),
|
|
59
|
+
config: merge(
|
|
60
|
+
{
|
|
61
|
+
credentials: {
|
|
62
|
+
idbroker: {
|
|
63
|
+
url: process.env.IDBROKER_BASE_URL,
|
|
64
|
+
defaultUrl: process.env.IDBROKER_BASE_URL,
|
|
65
|
+
},
|
|
66
|
+
identity: {
|
|
67
|
+
url: process.env.IDENTITY_BASE_URL,
|
|
68
|
+
defaultUrl: process.env.IDENTITY_BASE_URL,
|
|
69
|
+
},
|
|
70
|
+
activationUrl: `${
|
|
71
|
+
process.env.IDBROKER_BASE_URL || 'https://idbroker.webex.com'
|
|
72
|
+
}/idb/token/v1/actions/UserActivation/invoke`,
|
|
73
|
+
authorizeUrl: `${
|
|
74
|
+
process.env.IDBROKER_BASE_URL || 'https://idbroker.webex.com'
|
|
75
|
+
}/idb/oauth2/v1/authorize`,
|
|
76
|
+
setPasswordUrl: `${
|
|
77
|
+
process.env.IDBROKER_BASE_URL || 'https://identity.webex.com'
|
|
78
|
+
}/identity/scim/v1/Users`,
|
|
79
|
+
logoutUrl: `${
|
|
80
|
+
process.env.IDBROKER_BASE_URL || 'https://idbroker.webex.com'
|
|
81
|
+
}/idb/oauth2/v1/logout`,
|
|
82
|
+
// eslint-disable-next-line camelcase
|
|
83
|
+
client_id: 'fake',
|
|
84
|
+
// eslint-disable-next-line camelcase
|
|
85
|
+
client_secret: 'fake',
|
|
86
|
+
// eslint-disable-next-line camelcase
|
|
87
|
+
redirect_uri: 'http://example.com',
|
|
88
|
+
// eslint-disable-next-line camelcase
|
|
89
|
+
scope: 'scope:one',
|
|
90
|
+
refreshCallback: () => Promise.resolve(),
|
|
64
91
|
},
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
logoutUrl: `${process.env.IDBROKER_BASE_URL || 'https://idbroker.webex.com'}/idb/oauth2/v1/logout`,
|
|
69
|
-
// eslint-disable-next-line camelcase
|
|
70
|
-
client_id: 'fake',
|
|
71
|
-
// eslint-disable-next-line camelcase
|
|
72
|
-
client_secret: 'fake',
|
|
73
|
-
// eslint-disable-next-line camelcase
|
|
74
|
-
redirect_uri: 'http://example.com',
|
|
75
|
-
// eslint-disable-next-line camelcase
|
|
76
|
-
scope: 'scope:one',
|
|
77
|
-
refreshCallback: () => Promise.resolve()
|
|
78
|
-
}
|
|
79
|
-
}, config),
|
|
92
|
+
},
|
|
93
|
+
config
|
|
94
|
+
),
|
|
80
95
|
getWindow() {
|
|
81
96
|
return mockWindow;
|
|
82
|
-
}
|
|
97
|
+
},
|
|
83
98
|
});
|
|
84
99
|
|
|
85
100
|
return webex;
|
|
@@ -93,15 +108,14 @@ browserOnly(describe)('plugin-authorization-browser-first-party', () => {
|
|
|
93
108
|
assert.isFalse(webex.authorization.ready);
|
|
94
109
|
assert.isFalse(webex.credentials.canAuthorize);
|
|
95
110
|
|
|
96
|
-
return webex.authorization.when('change:ready')
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
});
|
|
111
|
+
return webex.authorization.when('change:ready').then(() => {
|
|
112
|
+
// Webex request gets called twice:
|
|
113
|
+
// once for the pre-auth catalog
|
|
114
|
+
// once for auth token exchange
|
|
115
|
+
assert.calledTwice(webex.request);
|
|
116
|
+
assert.isTrue(webex.authorization.ready);
|
|
117
|
+
assert.isTrue(webex.credentials.canAuthorize);
|
|
118
|
+
});
|
|
105
119
|
});
|
|
106
120
|
|
|
107
121
|
it('validates the csrf token', () => {
|
|
@@ -109,12 +123,20 @@ browserOnly(describe)('plugin-authorization-browser-first-party', () => {
|
|
|
109
123
|
|
|
110
124
|
assert.throws(() => {
|
|
111
125
|
// eslint-disable-next-line no-unused-vars
|
|
112
|
-
const webex = makeWebex(
|
|
126
|
+
const webex = makeWebex(
|
|
127
|
+
`http://example.com/?code=5&state=${base64.encode(
|
|
128
|
+
JSON.stringify({csrf_token: 'someothertoken'})
|
|
129
|
+
)}`,
|
|
130
|
+
csrfToken
|
|
131
|
+
);
|
|
113
132
|
}, /CSRF token someothertoken does not match stored token abcd/);
|
|
114
133
|
|
|
115
134
|
assert.throws(() => {
|
|
116
135
|
// eslint-disable-next-line no-unused-vars
|
|
117
|
-
const webex = makeWebex(
|
|
136
|
+
const webex = makeWebex(
|
|
137
|
+
`http://example.com/?code=5&state=${base64.encode(JSON.stringify({}))}`,
|
|
138
|
+
csrfToken
|
|
139
|
+
);
|
|
118
140
|
}, /Expected CSRF token abcd, but not found in redirect query/);
|
|
119
141
|
|
|
120
142
|
assert.throws(() => {
|
|
@@ -122,33 +144,46 @@ browserOnly(describe)('plugin-authorization-browser-first-party', () => {
|
|
|
122
144
|
const webex = makeWebex('http://example.com/?code=5', csrfToken);
|
|
123
145
|
}, /Expected CSRF token abcd, but not found in redirect query/);
|
|
124
146
|
|
|
125
|
-
const webex = makeWebex(
|
|
147
|
+
const webex = makeWebex(
|
|
148
|
+
`http://example.com/?code=5&state=${base64.encode(
|
|
149
|
+
JSON.stringify({csrf_token: csrfToken})
|
|
150
|
+
)}`,
|
|
151
|
+
csrfToken
|
|
152
|
+
);
|
|
126
153
|
|
|
127
|
-
return webex.authorization.when('change:ready')
|
|
128
|
-
.
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
});
|
|
154
|
+
return webex.authorization.when('change:ready').then(() => {
|
|
155
|
+
assert.isTrue(webex.credentials.canAuthorize);
|
|
156
|
+
assert.called(webex.getWindow().sessionStorage.removeItem);
|
|
157
|
+
});
|
|
132
158
|
});
|
|
133
159
|
|
|
134
160
|
it('removes the oauth parameters from the url', () => {
|
|
135
161
|
const csrfToken = 'abcd';
|
|
136
162
|
|
|
137
|
-
const webex = makeWebex(
|
|
163
|
+
const webex = makeWebex(
|
|
164
|
+
`http://example.com/?code=5&state=${base64.encode(
|
|
165
|
+
JSON.stringify({csrf_token: csrfToken, something: true})
|
|
166
|
+
)}`,
|
|
167
|
+
csrfToken
|
|
168
|
+
);
|
|
138
169
|
|
|
139
|
-
return webex.authorization.when('change:ready')
|
|
140
|
-
.
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
170
|
+
return webex.authorization.when('change:ready').then(() => {
|
|
171
|
+
assert.isTrue(webex.credentials.canAuthorize);
|
|
172
|
+
assert.called(webex.getWindow().sessionStorage.removeItem);
|
|
173
|
+
assert.called(webex.getWindow().history.replaceState);
|
|
174
|
+
assert.equal(
|
|
175
|
+
webex.getWindow().location.href,
|
|
176
|
+
`http://example.com/?state=${base64.encode(JSON.stringify({something: true}))}`
|
|
177
|
+
);
|
|
178
|
+
});
|
|
146
179
|
});
|
|
147
180
|
});
|
|
148
181
|
describe('when the url contains an error', () => {
|
|
149
182
|
it('throws a grant error', () => {
|
|
150
183
|
assert.throws(() => {
|
|
151
|
-
makeWebex(
|
|
184
|
+
makeWebex(
|
|
185
|
+
'http://127.0.0.1:8000/?error=invalid_scope&error_description=The%20requested%20scope%20is%20invalid.'
|
|
186
|
+
);
|
|
152
187
|
}, /The requested scope is invalid./);
|
|
153
188
|
});
|
|
154
189
|
});
|
|
@@ -166,28 +201,14 @@ browserOnly(describe)('plugin-authorization-browser-first-party', () => {
|
|
|
166
201
|
it('passes codeVerifier to requestAuthorizationCodeGrant', () => {
|
|
167
202
|
const expectedVerifier = 'test verifier';
|
|
168
203
|
|
|
169
|
-
const webex = makeWebex(
|
|
170
|
-
'http://example.com?code=5',
|
|
171
|
-
undefined,
|
|
172
|
-
expectedVerifier
|
|
173
|
-
);
|
|
204
|
+
const webex = makeWebex('http://example.com?code=5', undefined, expectedVerifier);
|
|
174
205
|
|
|
175
|
-
return webex.authorization.when('change:ready')
|
|
176
|
-
.
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
);
|
|
182
|
-
assert.calledWith(
|
|
183
|
-
webex.getWindow().sessionStorage.removeItem,
|
|
184
|
-
'oauth2-code-verifier'
|
|
185
|
-
);
|
|
186
|
-
assert.equal(
|
|
187
|
-
webex.request.getCall(1).args[0].form.code_verifier,
|
|
188
|
-
expectedVerifier
|
|
189
|
-
);
|
|
190
|
-
});
|
|
206
|
+
return webex.authorization.when('change:ready').then(() => {
|
|
207
|
+
assert.calledTwice(webex.request);
|
|
208
|
+
assert.calledWith(webex.getWindow().sessionStorage.getItem, 'oauth2-code-verifier');
|
|
209
|
+
assert.calledWith(webex.getWindow().sessionStorage.removeItem, 'oauth2-code-verifier');
|
|
210
|
+
assert.equal(webex.request.getCall(1).args[0].form.code_verifier, expectedVerifier);
|
|
211
|
+
});
|
|
191
212
|
});
|
|
192
213
|
});
|
|
193
214
|
});
|
|
@@ -196,95 +217,97 @@ browserOnly(describe)('plugin-authorization-browser-first-party', () => {
|
|
|
196
217
|
it('calls #initiateAuthorizationCodeGrant()', () => {
|
|
197
218
|
const webex = makeWebex(undefined, undefined, {
|
|
198
219
|
credentials: {
|
|
199
|
-
clientType: 'confidential'
|
|
200
|
-
}
|
|
220
|
+
clientType: 'confidential',
|
|
221
|
+
},
|
|
201
222
|
});
|
|
202
223
|
|
|
203
224
|
sinon.spy(webex.authorization, 'initiateAuthorizationCodeGrant');
|
|
204
225
|
|
|
205
|
-
return webex.authorization.initiateLogin()
|
|
206
|
-
.
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
});
|
|
226
|
+
return webex.authorization.initiateLogin().then(() => {
|
|
227
|
+
assert.called(webex.authorization.initiateAuthorizationCodeGrant);
|
|
228
|
+
assert.include(webex.getWindow().location, 'response_type=code');
|
|
229
|
+
});
|
|
210
230
|
});
|
|
211
231
|
|
|
212
232
|
it('adds a csrf_token to the login url and sessionStorage', () => {
|
|
213
233
|
const webex = makeWebex(undefined, undefined, {
|
|
214
234
|
credentials: {
|
|
215
|
-
clientType: 'confidential'
|
|
216
|
-
}
|
|
235
|
+
clientType: 'confidential',
|
|
236
|
+
},
|
|
217
237
|
});
|
|
218
238
|
|
|
219
239
|
sinon.spy(webex.authorization, 'initiateAuthorizationCodeGrant');
|
|
220
240
|
|
|
221
|
-
return webex.authorization.initiateLogin()
|
|
222
|
-
.
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
241
|
+
return webex.authorization.initiateLogin().then(() => {
|
|
242
|
+
assert.called(webex.authorization.initiateAuthorizationCodeGrant);
|
|
243
|
+
assert.include(webex.getWindow().location, 'response_type=code');
|
|
244
|
+
const {query} = url.parse(webex.getWindow().location, true);
|
|
245
|
+
let {state} = query;
|
|
246
|
+
|
|
247
|
+
state = JSON.parse(base64.decode(state));
|
|
248
|
+
assert.property(state, 'csrf_token');
|
|
249
|
+
assert.isDefined(state.csrf_token);
|
|
250
|
+
assert.match(state.csrf_token, patterns.uuid);
|
|
251
|
+
assert.called(webex.getWindow().sessionStorage.setItem);
|
|
252
|
+
assert.calledWith(
|
|
253
|
+
webex.getWindow().sessionStorage.setItem,
|
|
254
|
+
'oauth2-csrf-token',
|
|
255
|
+
state.csrf_token
|
|
256
|
+
);
|
|
257
|
+
});
|
|
235
258
|
});
|
|
236
259
|
|
|
237
260
|
it('adds a pkce code challenge', () => {
|
|
238
261
|
const webex = makeWebex(undefined, undefined, {
|
|
239
262
|
credentials: {
|
|
240
|
-
clientType: 'confidential'
|
|
241
|
-
}
|
|
263
|
+
clientType: 'confidential',
|
|
264
|
+
},
|
|
242
265
|
});
|
|
243
266
|
|
|
244
267
|
const expectedCodeChallenge = 'test challenge';
|
|
245
268
|
|
|
246
269
|
sinon.spy(webex.authorization, 'initiateAuthorizationCodeGrant');
|
|
247
|
-
sinon.stub(webex.authorization, '_generateCodeChallenge')
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
});
|
|
270
|
+
sinon.stub(webex.authorization, '_generateCodeChallenge').returns(expectedCodeChallenge);
|
|
271
|
+
|
|
272
|
+
return webex.authorization.initiateLogin().then(() => {
|
|
273
|
+
assert.called(webex.authorization.initiateAuthorizationCodeGrant);
|
|
274
|
+
const grantOptions =
|
|
275
|
+
webex.authorization.initiateAuthorizationCodeGrant.getCall(0).args[0];
|
|
276
|
+
|
|
277
|
+
assert.equal(grantOptions.code_challenge, expectedCodeChallenge);
|
|
278
|
+
assert.equal(grantOptions.code_challenge_method, 'S256');
|
|
279
|
+
// eslint-disable-next-line no-underscore-dangle
|
|
280
|
+
assert.calledWith(webex.authorization._generateCodeChallenge);
|
|
281
|
+
});
|
|
260
282
|
});
|
|
261
283
|
|
|
262
284
|
it('adds emailHash', () => {
|
|
263
285
|
const webex = makeWebex(undefined, undefined, {
|
|
264
286
|
credentials: {
|
|
265
|
-
clientType: 'confidential'
|
|
266
|
-
}
|
|
287
|
+
clientType: 'confidential',
|
|
288
|
+
},
|
|
267
289
|
});
|
|
268
290
|
|
|
269
|
-
const expectedEmailHash =
|
|
291
|
+
const expectedEmailHash =
|
|
292
|
+
'73062d872926c2a556f17b36f50e328ddf9bff9d403939bd14b6c3b7f5a33fc2';
|
|
270
293
|
|
|
271
294
|
sinon.spy(webex.authorization, 'initiateAuthorizationCodeGrant');
|
|
272
295
|
|
|
273
|
-
return webex.authorization.initiateLogin({email: 'test@email.com'})
|
|
274
|
-
.
|
|
275
|
-
|
|
276
|
-
|
|
296
|
+
return webex.authorization.initiateLogin({email: 'test@email.com'}).then(() => {
|
|
297
|
+
assert.called(webex.authorization.initiateAuthorizationCodeGrant);
|
|
298
|
+
const grantOptions =
|
|
299
|
+
webex.authorization.initiateAuthorizationCodeGrant.getCall(0).args[0];
|
|
277
300
|
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
301
|
+
assert.equal(grantOptions.emailHash, expectedEmailHash);
|
|
302
|
+
assert.isUndefined(grantOptions.email);
|
|
303
|
+
});
|
|
281
304
|
});
|
|
282
305
|
|
|
283
306
|
it('sets #isAuthorizing', () => {
|
|
284
307
|
const webex = makeWebex(undefined, undefined, {
|
|
285
308
|
credentials: {
|
|
286
|
-
clientType: 'confidential'
|
|
287
|
-
}
|
|
309
|
+
clientType: 'confidential',
|
|
310
|
+
},
|
|
288
311
|
});
|
|
289
312
|
|
|
290
313
|
assert.isFalse(webex.authorization.isAuthorizing);
|
|
@@ -298,8 +321,8 @@ browserOnly(describe)('plugin-authorization-browser-first-party', () => {
|
|
|
298
321
|
it('sets #isAuthenticating', () => {
|
|
299
322
|
const webex = makeWebex(undefined, undefined, {
|
|
300
323
|
credentials: {
|
|
301
|
-
clientType: 'confidential'
|
|
302
|
-
}
|
|
324
|
+
clientType: 'confidential',
|
|
325
|
+
},
|
|
303
326
|
});
|
|
304
327
|
|
|
305
328
|
assert.isFalse(webex.authorization.isAuthenticating);
|
|
@@ -315,17 +338,16 @@ browserOnly(describe)('plugin-authorization-browser-first-party', () => {
|
|
|
315
338
|
it('redirects to the login page with response_type=code', () => {
|
|
316
339
|
const webex = makeWebex(undefined, undefined, {
|
|
317
340
|
credentials: {
|
|
318
|
-
clientType: 'confidential'
|
|
319
|
-
}
|
|
341
|
+
clientType: 'confidential',
|
|
342
|
+
},
|
|
320
343
|
});
|
|
321
344
|
|
|
322
345
|
sinon.spy(webex.authorization, 'initiateAuthorizationCodeGrant');
|
|
323
346
|
|
|
324
|
-
return webex.authorization.initiateLogin()
|
|
325
|
-
.
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
});
|
|
347
|
+
return webex.authorization.initiateLogin().then(() => {
|
|
348
|
+
assert.called(webex.authorization.initiateAuthorizationCodeGrant);
|
|
349
|
+
assert.include(webex.getWindow().location, 'response_type=code');
|
|
350
|
+
});
|
|
329
351
|
});
|
|
330
352
|
});
|
|
331
353
|
|
|
@@ -342,7 +364,7 @@ browserOnly(describe)('plugin-authorization-browser-first-party', () => {
|
|
|
342
364
|
const toStringStub = sinon.stub().returns(expectedCodeChallenge);
|
|
343
365
|
const randomStub = sinon.stub(lodash, 'random').returns(0);
|
|
344
366
|
const sha256Stub = sinon.stub(CryptoJS, 'SHA256').returns({
|
|
345
|
-
toString: toStringStub
|
|
367
|
+
toString: toStringStub,
|
|
346
368
|
});
|
|
347
369
|
|
|
348
370
|
// eslint-disable-next-line no-underscore-dangle
|
|
@@ -365,16 +387,16 @@ browserOnly(describe)('plugin-authorization-browser-first-party', () => {
|
|
|
365
387
|
it('removes the state parameter when it has no keys', () => {
|
|
366
388
|
const webex = makeWebex(undefined, undefined, {
|
|
367
389
|
credentials: {
|
|
368
|
-
clientType: 'confidential'
|
|
369
|
-
}
|
|
390
|
+
clientType: 'confidential',
|
|
391
|
+
},
|
|
370
392
|
});
|
|
371
393
|
const location = {
|
|
372
394
|
query: {
|
|
373
395
|
code: 'code',
|
|
374
396
|
state: {
|
|
375
|
-
csrf_token: 'token'
|
|
376
|
-
}
|
|
377
|
-
}
|
|
397
|
+
csrf_token: 'token',
|
|
398
|
+
},
|
|
399
|
+
},
|
|
378
400
|
};
|
|
379
401
|
|
|
380
402
|
sinon.spy(webex.authorization, '_cleanUrl');
|
|
@@ -386,17 +408,17 @@ browserOnly(describe)('plugin-authorization-browser-first-party', () => {
|
|
|
386
408
|
it('keeps the parameter when it has keys', () => {
|
|
387
409
|
const webex = makeWebex(undefined, undefined, {
|
|
388
410
|
credentials: {
|
|
389
|
-
clientType: 'confidential'
|
|
390
|
-
}
|
|
411
|
+
clientType: 'confidential',
|
|
412
|
+
},
|
|
391
413
|
});
|
|
392
414
|
const location = {
|
|
393
415
|
query: {
|
|
394
416
|
code: 'code',
|
|
395
417
|
state: {
|
|
396
418
|
csrf_token: 'token',
|
|
397
|
-
key: 'value'
|
|
398
|
-
}
|
|
399
|
-
}
|
|
419
|
+
key: 'value',
|
|
420
|
+
},
|
|
421
|
+
},
|
|
400
422
|
};
|
|
401
423
|
|
|
402
424
|
sinon.spy(webex.authorization, '_cleanUrl');
|