Skip to content

Commit 85a04fa

Browse files
authoredFeb 25, 2020
feat: client_{id,_secret} are no longer passed as query, but basic authentication only (#41)
BREAKING CHANGE: `:client_id` and `:access_token` URL parameters are no longer set by default BREAKING CHANGE: `client_id` and `client_secret` are now passed as basic authentication for any URL BREAKING CHANGE: The `url` option has been removed for `auth({ type: "app" })` BREAKING CHANGE: `auth({ type: "app" })` no longer returns a `.query` key
1 parent e224558 commit 85a04fa

File tree

6 files changed

+162
-256
lines changed

6 files changed

+162
-256
lines changed
 

‎README.md

+18-58
Original file line numberDiff line numberDiff line change
@@ -16,8 +16,8 @@ It implements authentication using an OAuth app’s client ID and secret as well
1616
- [`createOAuthAppAuth(options)`](#createoauthappauthoptions)
1717
- [`auth()`](#auth)
1818
- [Authentication object](#authentication-object)
19-
- [OAuth authentication](#oauth-authentication)
20-
- [OAuth access token authentication](#oauth-access-token-authentication)
19+
- [OAuth authentication](#oauth-authentication)
20+
- [OAuth access token authentication](#oauth-access-token-authentication)
2121
- [`auth.hook(request, route, parameters)` or `auth.hook(request, options)`](#authhookrequest-route-parameters-or-authhookrequest-options)
2222
- [Implementation details](#implementation-details)
2323
- [License](#license)
@@ -62,20 +62,18 @@ const auth = createOAuthAppAuth({
6262
clientSecret: "secret"
6363
});
6464

65-
// OAuth Apps authenticate using ?client_id=...&client_secret=... query parameters
66-
// or Basic auth, depending on the request URL (see implementation details below).
65+
// OAuth Apps authenticate using Basic auth, where
66+
// username is clientId and password is clientSecret
6767
const appAuthentication = await auth({
68-
type: "oauth-app",
69-
url: "/orgs/:org/repos"
68+
type: "oauth-app"
7069
});
7170
// resolves with
7271
// {
7372
// type: 'oauth-app',
7473
// clientId: '123',
7574
// clientSecret: 'secret',
76-
// query: {
77-
// client_id: '123',
78-
// client_secret: 'secret'
75+
// headers: {
76+
// authorization: 'basic MTIzOnNlY3JldA=='
7977
// }
8078
// }
8179

@@ -222,22 +220,6 @@ The async `auth()` method returned by `createOAuthAppAuth(options)` accepts the
222220
<strong>Required.</strong> Either <code>"oauth-app"</code> or <code>"token"</code>.
223221
</td>
224222
</tr>
225-
<tr>
226-
<th>
227-
<code>options.url</code>
228-
</th>
229-
<th>
230-
<code>string</code>
231-
</th>
232-
<td>
233-
<strong>Required if <code>options.type</code> set to <code>"oauth-app"</code>.</strong> An absolute URL or endpoint route path. Examples:
234-
<ul>
235-
<li><code>"https://enterprise.github.com/api/v3/applications/1234567890abcdef1234/tokens/secret123"</code></li>
236-
<li><code>"/applications/1234567890abcdef1234/tokens/secret123"</code></li>
237-
<li><code>"/applications/:client_id/tokens/:access_token"</code></li>
238-
</ul>
239-
</td>
240-
</tr>
241223
<tr>
242224
<th>
243225
<code>options.code</code>
@@ -339,22 +321,7 @@ The async `auth(options)` method to one of two possible authentication objects
339321
<code>object</code>
340322
</th>
341323
<td>
342-
<code>{}</code> if no <code>url</code> option was passed or the passed <code>url</code> option <em>does not</em> match <code>/applications/:client_id/tokens/:access_token</code>.<br>
343-
<br>
344-
<code>{ authorization }</code> if the passed <code>url</code> option <em>does</em> match <code>/applications/:client_id/tokens/:access_token</code>.
345-
</td>
346-
</tr>
347-
<tr>
348-
<th>
349-
<code>query</code>
350-
</th>
351-
<th>
352-
<code>object</code>
353-
</th>
354-
<td>
355-
<code>{ client_id, client_secret }</code> if no <code>url</code> option was passed or the passed <code>url</code> option <em>does not</em> match <code>/applications/:client_id/tokens/:access_token</code>.<br>
356-
<br>
357-
<code>{}</code> if the passed <code>url</code> option <em>does</em> match <code>/applications/:client_id/tokens/:access_token</code>.
324+
<code>{ authorization }</code>.
358325
</td>
359326
</tr>
360327
</tbody>
@@ -433,10 +400,7 @@ The `request` option is an instance of [`@octokit/request`](https://github.com/o
433400
`auth.hook()` can be called directly to send an authenticated request
434401

435402
```js
436-
const { data: authorizations } = await auth.hook(
437-
request,
438-
"GET /applications/:client_id/tokens/:access_token"
439-
);
403+
const { data: user } = await auth.hook(request, "GET /user");
440404
```
441405

442406
Or it can be passed as option to [`request()`](https://github.com/octokit/request.js#request).
@@ -448,27 +412,23 @@ const requestWithAuth = request.defaults({
448412
}
449413
});
450414

451-
const { data: authorization } = await requestWithAuth(
452-
"GET /applications/:client_id/tokens/:access_token"
453-
);
415+
const { data: user } = await requestWithAuth("GET /user");
454416
```
455417

456418
## Implementation details
457419

458-
Client ID and secret can be passed as URL query parameters (`?client_id=...&client_secret=...`) to get a higher rate limit compared to unauthenticated requests. This is meant for the use on servers only: never expose an OAuth client secret on a client such as a web application!
459-
460-
The only exceptions are
420+
Client ID and secret can be passed as Basic auth in the `Authorization` header in order to get a higher rate limit compared to unauthenticated requests. This is meant for the use on servers only: never expose an OAuth client secret on a client such as a web application!
461421

462-
- [`GET /applications/:client_id/tokens/:access_token`](https://developer.github.com/v3/oauth_authorizations/#check-an-authorization) - Check an authorization
463-
- [`POST /applications/:client_id/tokens/:access_token`](https://developer.github.com/v3/oauth_authorizations/#reset-an-authorization) - Reset an authorization
464-
- [`DELETE /applications/:client_id/tokens/:access_token`](https://developer.github.com/v3/oauth_authorizations/#revoke-an-authorization-for-an-application) - Revoke an authorization for an application
422+
`auth.hook` will set the correct authentication header automatically based on the request URL. For all [OAuth Application endpoints](https://developer.github.com/v3/apps/oauth_applications/), the `Authorization` header is set to basic auth. For all other endpoints and token is retrieved and used in the `Authorization` header. The token is cached and used for succeeding requsets.
465423

466-
For these endpoints, client ID and secret need to be passed as basic authentication in the `Authorization` header. Because of these exception an `options.url` parameter must be passed to the async `auth()` function if `options.type` is set to `oauth-app`. Additionally, `:client_id` and `:access_token` are defaulted to `options.clientId` passed to `createOAuthAppAuth(options)` and the token which was created using `options.code`, if passed.
467-
468-
To reset the current access token, you can do this
424+
To reset the cached access token, you can do this
469425

470426
```js
471-
await auth.hook(request, "POST /applications/:client_id/tokens/:access_token");
427+
const { token } = await auth({ type: "token" });
428+
await auth.hook(request, "POST /applications/:client_id/token", {
429+
client_id: "123",
430+
access_token: token
431+
});
472432
```
473433

474434
The internally cached token will be replaced and used for succeeding requests. See also ["the REST API documentation"](https://developer.github.com/v3/oauth_authorizations/).

‎src/auth.ts

+3-19
Original file line numberDiff line numberDiff line change
@@ -21,28 +21,12 @@ export async function auth(
2121
};
2222
}
2323

24-
const [headers, query] = requiresBasicAuth(authOptions.url)
25-
? [
26-
{
27-
authorization: `basic ${btoa(
28-
`${state.clientId}:${state.clientSecret}`
29-
)}`
30-
},
31-
{}
32-
]
33-
: [
34-
{},
35-
{
36-
client_id: state.clientId,
37-
client_secret: state.clientSecret
38-
}
39-
];
40-
4124
return {
4225
type: "oauth-app",
4326
clientId: state.clientId,
4427
clientSecret: state.clientSecret,
45-
headers,
46-
query
28+
headers: {
29+
authorization: `basic ${btoa(`${state.clientId}:${state.clientSecret}`)}`
30+
}
4731
};
4832
}

‎src/hook.ts

+35-34
Original file line numberDiff line numberDiff line change
@@ -10,53 +10,54 @@ import {
1010
Route,
1111
State
1212
} from "./types";
13+
import { EndpointDefaults } from "@octokit/types";
1314

1415
export async function hook(
1516
state: State,
1617
request: RequestInterface,
1718
route: Route | EndpointOptions,
1819
parameters?: RequestParameters
1920
): Promise<AnyResponse> {
20-
let endpoint = request.endpoint.merge(route as string, parameters);
21+
let endpoint = request.endpoint.merge(
22+
route as string,
23+
parameters
24+
) as EndpointDefaults & { url: string };
2125

2226
// Do not intercept request to retrieve a new token
2327
if (/\/login\/oauth\/access_token$/.test(endpoint.url as string)) {
24-
return request(endpoint as EndpointOptions);
28+
return request(endpoint);
2529
}
2630

27-
const { token } = await getOAuthAccessToken(state, { request });
28-
29-
if (!requiresBasicAuth(endpoint.url)) {
30-
endpoint.headers.authorization = `token ${token}`;
31-
32-
return request(endpoint as EndpointOptions);
33-
}
34-
35-
const credentials = btoa(`${state.clientId}:${state.clientSecret}`);
36-
endpoint.headers.authorization = `basic ${credentials}`;
37-
38-
// default `:client_id` & `:access_token` URL parameters
39-
if (endpoint.url && /:client_id/.test(endpoint.url)) {
40-
endpoint = Object.assign(
41-
{
42-
client_id: state.clientId,
43-
access_token: token
44-
},
45-
endpoint
46-
);
31+
if (requiresBasicAuth(endpoint.url)) {
32+
const credentials = btoa(`${state.clientId}:${state.clientSecret}`);
33+
endpoint.headers.authorization = `basic ${credentials}`;
34+
35+
const response = await request(endpoint);
36+
37+
const parsedEndpoint = request.endpoint.parse(endpoint);
38+
// `POST /applications/:client_id/tokens/:access_token` (legacy) or
39+
// `PATCH /applications/:client_id/token` resets the passed token
40+
// and returns a new one. If that’s the current request then update internal state.
41+
const isLegacyTokenResetRequest =
42+
endpoint.method === "POST" &&
43+
/^\/applications\/:?[\w_]+\/tokens\/:?[\w_]+$/.test(endpoint.url);
44+
const isTokenResetRequest =
45+
endpoint.method === "PATCH" &&
46+
/^\/applications\/:?[\w_]+\/token$/.test(endpoint.url);
47+
48+
if (isLegacyTokenResetRequest || isTokenResetRequest) {
49+
state.token = {
50+
token: response.data.token,
51+
// @ts-ignore figure this out
52+
scope: response.data.scopes
53+
};
54+
}
55+
56+
return response;
4757
}
4858

49-
const response = await request(endpoint as EndpointOptions);
50-
51-
// `POST /applications/:client_id/tokens/:access_token` resets the passed token
52-
// and returns a new one. If that’s the current request then update internal state.
53-
const parsedEndpoint = request.endpoint.parse(endpoint);
54-
const isTokenResetRequest =
55-
parsedEndpoint.method === "POST" &&
56-
new RegExp(token).test(parsedEndpoint.url);
57-
if (isTokenResetRequest && state.token) {
58-
state.token.token = response.data.token;
59-
}
59+
const { token } = await getOAuthAccessToken(state, { request });
60+
endpoint.headers.authorization = `token ${token}`;
6061

61-
return response;
62+
return request(endpoint as EndpointOptions);
6263
}

‎src/requires-basic-auth.ts

+3-4
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
/**
2-
* An OAuth app authenticates using ?client_id=...&client_secret=... query parameters, with the
3-
* exception of these three endpoints, which require the client ID/secret to be sent as basic auth
2+
* The following endpoints require an OAuth App to authenticate using its client_id and client_secret.
43
*
54
* - [`POST /applications/:client_id/token`](https://developer.github.com/v3/apps/oauth_applications/#check-a-token) - Check a token
65
* - [`PATCH /applications/:client_id/token`](https://developer.github.com/v3/apps/oauth_applications/#reset-a-token) - Reset a token
@@ -14,8 +13,8 @@
1413
* - [`DELETE /applications/:client_id/tokens/:access_token`](https://developer.github.com/v3/apps/oauth_applications/#revoke-an-authorization-for-an-application) - Revoke an authorization for an application
1514
* - [`DELETE /applications/:client_id/grants/:access_token`](https://developer.github.com/v3/apps/oauth_applications/#revoke-a-grant-for-an-application) - Revoke a grant for an application
1615
*/
17-
const OAUTH_ROUTES_EXCEPTIONS = /\/applications\/:?[\w_]+\/(token|grant)(s\/:?[\w_]+)?($|\?)/;
16+
const ROUTES_REQUIRING_BASIC_AUTH = /\/applications\/:?[\w_]+\/(token|grant)(s\/:?[\w_]+)?($|\?)/;
1817

1918
export function requiresBasicAuth(url: string | undefined) {
20-
return url && OAUTH_ROUTES_EXCEPTIONS.test(url);
19+
return url && ROUTES_REQUIRING_BASIC_AUTH.test(url);
2120
}

‎src/types.ts

+1-6
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,6 @@ export type StrategyOptions = {
2222

2323
type AuthAppOptions = {
2424
type: "oauth-app";
25-
url: string;
2625
};
2726
export type AuthTokenOptions = {
2827
type: "token";
@@ -46,11 +45,7 @@ export type appAuthentication = {
4645
clientId: string;
4746
clientSecret: string;
4847
headers: {
49-
authorization?: string;
50-
};
51-
query: {
52-
client_id?: string;
53-
client_secret?: string;
48+
authorization: string;
5449
};
5550
};
5651
export type Authentication = TokenAuthentication | appAuthentication;

‎test/index.test.ts

+102-135
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ import { request } from "@octokit/request";
33

44
import { createOAuthAppAuth } from "../src/index";
55

6-
test("README example with `url`", async () => {
6+
test("README example with type: 'oauth-app'", async () => {
77
const auth = createOAuthAppAuth({
88
clientId: "123",
99
clientSecret: "secret",
@@ -12,23 +12,20 @@ test("README example with `url`", async () => {
1212
});
1313

1414
const authentication = await auth({
15-
type: "oauth-app",
16-
url: "/orgs/:org/repos"
15+
type: "oauth-app"
1716
});
1817

1918
expect(authentication).toEqual({
2019
type: "oauth-app",
2120
clientId: "123",
2221
clientSecret: "secret",
23-
headers: {},
24-
query: {
25-
client_id: "123",
26-
client_secret: "secret"
22+
headers: {
23+
authorization: "basic MTIzOnNlY3JldA==" // btoa('123:secret')
2724
}
2825
});
2926
});
3027

31-
test("README example with `auth: 'token'`", async () => {
28+
test("README example with `type: 'token'`", async () => {
3229
const mock = fetchMock.sandbox().postOnce(
3330
"https://github.com/login/oauth/access_token",
3431
{
@@ -78,78 +75,6 @@ test("README example with `auth: 'token'`", async () => {
7875
});
7976
});
8077

81-
test('`url` is "/applications/:client_id/token"', async () => {
82-
const auth = createOAuthAppAuth({
83-
clientId: "123",
84-
clientSecret: "secret",
85-
code: "random123",
86-
state: "mystate123"
87-
});
88-
89-
const authentication = await auth({
90-
type: "oauth-app",
91-
url: "/applications/:client_id/token"
92-
});
93-
94-
expect(authentication).toEqual({
95-
type: "oauth-app",
96-
clientId: "123",
97-
clientSecret: "secret",
98-
headers: {
99-
authorization: "basic MTIzOnNlY3JldA==" // btoa('123:secret')
100-
},
101-
query: {}
102-
});
103-
});
104-
105-
test('`url` is "/applications/:client_id/grant"', async () => {
106-
const auth = createOAuthAppAuth({
107-
clientId: "123",
108-
clientSecret: "secret",
109-
code: "random123",
110-
state: "mystate123"
111-
});
112-
113-
const authentication = await auth({
114-
type: "oauth-app",
115-
url: "/applications/:client_id/grant"
116-
});
117-
118-
expect(authentication).toEqual({
119-
type: "oauth-app",
120-
clientId: "123",
121-
clientSecret: "secret",
122-
headers: {
123-
authorization: "basic MTIzOnNlY3JldA==" // btoa('123:secret')
124-
},
125-
query: {}
126-
});
127-
});
128-
129-
test('`url` is "/applications/:client_id/tokens/:access_token" (deprecated)', async () => {
130-
const auth = createOAuthAppAuth({
131-
clientId: "123",
132-
clientSecret: "secret",
133-
code: "random123",
134-
state: "mystate123"
135-
});
136-
137-
const authentication = await auth({
138-
type: "oauth-app",
139-
url: "/applications/:client_id/tokens/secret123"
140-
});
141-
142-
expect(authentication).toEqual({
143-
type: "oauth-app",
144-
clientId: "123",
145-
clientSecret: "secret",
146-
headers: {
147-
authorization: "basic MTIzOnNlY3JldA==" // btoa('123:secret')
148-
},
149-
query: {}
150-
});
151-
});
152-
15378
test("`code`, `redirectUrl`, `state` set as strategyOptions", async () => {
15479
const matchCreateAccessToken: MockMatcherFunction = (
15580
url,
@@ -343,38 +268,63 @@ test("auth.hook() creates token and uses it for succeeding requests", async () =
343268
expect(mock.done()).toBe(true);
344269
});
345270

346-
test("auth.hook defaults URL parameters for '/applications/:client_id/tokens/:access_token'", async () => {
271+
test("auth.hook(request, 'POST https://github.com/login/oauth/access_token') does not send request twice (#35)", async () => {
272+
const mock = fetchMock
273+
.sandbox()
274+
.postOnce("https://github.com/login/oauth/access_token", {
275+
access_token: "secret123",
276+
scope: ""
277+
});
278+
279+
const auth = createOAuthAppAuth({
280+
clientId: "123",
281+
clientSecret: "secret"
282+
});
283+
284+
const requestWithAuth = request.defaults({
285+
request: {
286+
fetch: mock,
287+
hook: auth.hook
288+
}
289+
});
290+
291+
await requestWithAuth("POST https://github.com/login/oauth/access_token", {
292+
headers: {
293+
accept: "application/json"
294+
},
295+
type: "token",
296+
code: "random123",
297+
state: "mystate123"
298+
});
299+
});
300+
301+
test("auth.hook(request, 'POST /applications/:client_id/tokens/:access_token') resets the used token (legacy endpoint)", async () => {
347302
const mock = fetchMock
348303
.sandbox()
349304
.postOnce("https://github.com/login/oauth/access_token", {
350305
access_token: "secret123",
351306
scope: ""
352307
})
353308
.getOnce(
354-
"https://api.github.com/applications/123/tokens/secret123",
309+
"https://api.github.com/user",
355310
{ id: 123 },
356311
{
357312
headers: {
358-
authorization: "basic MTIzOnNlY3JldA==" // btoa('123:secret')
359-
}
360-
}
361-
)
362-
.getOnce(
363-
"https://api.github.com/applications/123/tokens/othersecret",
364-
{ id: 456 },
365-
{
366-
headers: {
367-
authorization: "basic MTIzOnNlY3JldA==" // btoa('123:secret')
313+
authorization: "token secret123"
368314
}
369315
}
370316
)
317+
.postOnce("https://api.github.com/applications/123/tokens/secret123", {
318+
token: "newsecret123"
319+
})
371320
.getOnce(
372-
"https://api.github.com/applications/123/tokens/yetanothersecret",
373-
{ id: 789 },
321+
"https://api.github.com/user",
322+
{ id: 123 },
374323
{
375324
headers: {
376-
authorization: "basic MTIzOnNlY3JldA==" // btoa('123:secret')
377-
}
325+
authorization: "token newsecret123"
326+
},
327+
overwriteRoutes: false
378328
}
379329
);
380330

@@ -385,47 +335,49 @@ test("auth.hook defaults URL parameters for '/applications/:client_id/tokens/:ac
385335
state: "mystate123"
386336
});
387337

388-
const requestWithMock = request.defaults({
389-
request: {
390-
fetch: mock
391-
}
392-
});
393-
const requestWithAuth = requestWithMock.defaults({
338+
const requestWithAuth = request.defaults({
394339
request: {
340+
fetch: mock,
395341
hook: auth.hook
396342
}
397343
});
398344

399-
const { data: data1 } = await requestWithAuth(
400-
"GET /applications/:client_id/tokens/:access_token"
401-
);
402-
const {
403-
data: data2
404-
} = await requestWithAuth(
405-
"GET /applications/:client_id/tokens/:access_token",
406-
{ access_token: "othersecret" }
407-
);
408-
const { data: data3 } = await requestWithAuth(
409-
"GET /applications/123/tokens/yetanothersecret"
410-
);
345+
const response1 = await requestWithAuth("GET /user");
346+
expect(response1.data).toStrictEqual({ id: 123 });
411347

412-
expect(mock.done()).toBe(true);
413-
expect(data1.id).toBe(123);
414-
expect(data2.id).toBe(456);
415-
expect(data3.id).toBe(789);
348+
await requestWithAuth("POST /applications/:client_id/tokens/:access_token", {
349+
client_id: "123",
350+
access_token: "secret123"
351+
});
352+
353+
const response2 = await requestWithAuth("GET /user");
354+
expect(response2.data).toStrictEqual({ id: 123 });
416355
});
417356

418-
test("auth.hook(request, 'POST https://github.com/login/oauth/access_token') does not send request twice (#35)", async () => {
357+
test("auth.hook(request, 'POST /applications/:client_id/token') checks token", async () => {
419358
const mock = fetchMock
420359
.sandbox()
421360
.postOnce("https://github.com/login/oauth/access_token", {
422361
access_token: "secret123",
423362
scope: ""
424-
});
363+
})
364+
.postOnce(
365+
"https://api.github.com/applications/123/token",
366+
{
367+
token: "secret123"
368+
},
369+
{
370+
body: {
371+
access_token: "secret123"
372+
}
373+
}
374+
);
425375

426376
const auth = createOAuthAppAuth({
427377
clientId: "123",
428-
clientSecret: "secret"
378+
clientSecret: "secret",
379+
code: "random123",
380+
state: "mystate123"
429381
});
430382

431383
const requestWithAuth = request.defaults({
@@ -435,17 +387,20 @@ test("auth.hook(request, 'POST https://github.com/login/oauth/access_token') doe
435387
}
436388
});
437389

438-
await requestWithAuth("POST https://github.com/login/oauth/access_token", {
439-
headers: {
440-
accept: "application/json"
441-
},
442-
type: "token",
443-
code: "random123",
444-
state: "mystate123"
390+
const response = await requestWithAuth(
391+
"POST /applications/:client_id/token",
392+
{
393+
client_id: "123",
394+
access_token: "secret123"
395+
}
396+
);
397+
398+
expect(response.data).toStrictEqual({
399+
token: "secret123"
445400
});
446401
});
447402

448-
test("auth.hook(request, 'POST /applications/:client_id/tokens/:access_token') resets the used token", async () => {
403+
test("auth.hook(request, 'PATCH /applications/:client_id/token') resets the used token", async () => {
449404
const mock = fetchMock
450405
.sandbox()
451406
.postOnce("https://github.com/login/oauth/access_token", {
@@ -457,19 +412,27 @@ test("auth.hook(request, 'POST /applications/:client_id/tokens/:access_token') r
457412
{ id: 123 },
458413
{
459414
headers: {
460-
authorization: "token secret123" // btoa('123:secret')
415+
authorization: "token secret123"
416+
}
417+
}
418+
)
419+
.patchOnce(
420+
"https://api.github.com/applications/123/token",
421+
{
422+
token: "newsecret123"
423+
},
424+
{
425+
body: {
426+
access_token: "secret123"
461427
}
462428
}
463429
)
464-
.postOnce("https://api.github.com/applications/123/tokens/secret123", {
465-
token: "newsecret123"
466-
})
467430
.getOnce(
468431
"https://api.github.com/user",
469432
{ id: 123 },
470433
{
471434
headers: {
472-
authorization: "token newsecret123" // btoa('123:secret')
435+
authorization: "token newsecret123"
473436
},
474437
overwriteRoutes: false
475438
}
@@ -492,7 +455,11 @@ test("auth.hook(request, 'POST /applications/:client_id/tokens/:access_token') r
492455
const response1 = await requestWithAuth("GET /user");
493456
expect(response1.data).toStrictEqual({ id: 123 });
494457

495-
await requestWithAuth("POST /applications/:client_id/tokens/:access_token");
458+
await requestWithAuth("PATCH /applications/:client_id/token", {
459+
client_id: "123",
460+
access_token: "secret123"
461+
});
462+
496463
const response2 = await requestWithAuth("GET /user");
497464
expect(response2.data).toStrictEqual({ id: 123 });
498465
});

0 commit comments

Comments
 (0)
Please sign in to comment.