nuxt-auth-utils 0.0.17 → 0.0.19
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 +3 -2
- package/dist/module.json +1 -1
- package/dist/module.mjs +15 -9
- package/dist/runtime/composables/session.d.ts +2 -10
- package/dist/runtime/composables/session.mjs +2 -2
- package/dist/runtime/server/lib/oauth/auth0.d.ts +6 -0
- package/dist/runtime/server/lib/oauth/auth0.mjs +5 -2
- package/dist/runtime/server/lib/oauth/battledotnet.d.ts +5 -0
- package/dist/runtime/server/lib/oauth/battledotnet.mjs +4 -2
- package/dist/runtime/server/lib/oauth/cognito.d.ts +5 -0
- package/dist/runtime/server/lib/oauth/cognito.mjs +5 -2
- package/dist/runtime/server/lib/oauth/discord.d.ts +6 -0
- package/dist/runtime/server/lib/oauth/discord.mjs +4 -2
- package/dist/runtime/server/lib/oauth/github.d.ts +6 -0
- package/dist/runtime/server/lib/oauth/github.mjs +17 -5
- package/dist/runtime/server/lib/oauth/google.d.ts +6 -0
- package/dist/runtime/server/lib/oauth/google.mjs +4 -2
- package/dist/runtime/server/lib/oauth/keycloak.d.ts +4 -0
- package/dist/runtime/server/lib/oauth/keycloak.mjs +5 -6
- package/dist/runtime/server/lib/oauth/linkedin.d.ts +5 -0
- package/dist/runtime/server/lib/oauth/linkedin.mjs +4 -2
- package/dist/runtime/server/lib/oauth/microsoft.d.ts +8 -3
- package/dist/runtime/server/lib/oauth/microsoft.mjs +5 -2
- package/dist/runtime/server/lib/oauth/spotify.d.ts +6 -0
- package/dist/runtime/server/lib/oauth/spotify.mjs +4 -2
- package/dist/runtime/server/lib/oauth/twitch.d.ts +6 -0
- package/dist/runtime/server/lib/oauth/twitch.mjs +4 -2
- package/dist/runtime/server/utils/session.d.ts +4 -2
- package/dist/runtime/server/utils/session.mjs +1 -4
- package/dist/runtime/types/index.d.ts +1 -1
- package/dist/runtime/types/oauth-config.d.ts +1 -2
- package/dist/runtime/types/session.d.ts +8 -0
- package/package.json +4 -2
package/README.md
CHANGED
|
@@ -53,9 +53,10 @@ export default defineNuxtConfig({
|
|
|
53
53
|
NUXT_SESSION_PASSWORD=password-with-at-least-32-characters
|
|
54
54
|
```
|
|
55
55
|
|
|
56
|
-
Nuxt Auth Utils
|
|
56
|
+
Nuxt Auth Utils generates one for you when running Nuxt in development the first time if no `NUXT_SESSION_PASSWORD` is set.
|
|
57
|
+
|
|
58
|
+
3. That's it! You can now add authentication to your Nuxt app ✨
|
|
57
59
|
|
|
58
|
-
4. That's it! You can now add authentication to your Nuxt app ✨
|
|
59
60
|
|
|
60
61
|
## Vue Composables
|
|
61
62
|
|
package/dist/module.json
CHANGED
package/dist/module.mjs
CHANGED
|
@@ -1,6 +1,8 @@
|
|
|
1
1
|
import { defineNuxtModule, createResolver, addImportsDir, addPlugin, addServerHandler } from '@nuxt/kit';
|
|
2
|
-
import {
|
|
2
|
+
import { join } from 'pathe';
|
|
3
3
|
import { defu } from 'defu';
|
|
4
|
+
import { randomUUID } from 'uncrypto';
|
|
5
|
+
import { readFile, writeFile } from 'node:fs/promises';
|
|
4
6
|
|
|
5
7
|
const module = defineNuxtModule({
|
|
6
8
|
meta: {
|
|
@@ -9,14 +11,8 @@ const module = defineNuxtModule({
|
|
|
9
11
|
},
|
|
10
12
|
// Default configuration options of the Nuxt module
|
|
11
13
|
defaults: {},
|
|
12
|
-
setup(options, nuxt) {
|
|
14
|
+
async setup(options, nuxt) {
|
|
13
15
|
const resolver = createResolver(import.meta.url);
|
|
14
|
-
if (!process.env.NUXT_SESSION_PASSWORD && !nuxt.options._prepare) {
|
|
15
|
-
const randomPassword = sha256(`${Date.now()}${Math.random()}`).slice(0, 32);
|
|
16
|
-
process.env.NUXT_SESSION_PASSWORD = randomPassword;
|
|
17
|
-
console.warn("No session password set, using a random password, please set NUXT_SESSION_PASSWORD in your .env file with at least 32 chars");
|
|
18
|
-
console.log(`NUXT_SESSION_PASSWORD=${randomPassword}`);
|
|
19
|
-
}
|
|
20
16
|
nuxt.options.alias["#auth-utils"] = resolver.resolve("./runtime/types/index");
|
|
21
17
|
addImportsDir(resolver.resolve("./runtime/composables"));
|
|
22
18
|
addPlugin(resolver.resolve("./runtime/plugins/session.server"));
|
|
@@ -54,11 +50,21 @@ const module = defineNuxtModule({
|
|
|
54
50
|
const runtimeConfig = nuxt.options.runtimeConfig;
|
|
55
51
|
runtimeConfig.session = defu(runtimeConfig.session, {
|
|
56
52
|
name: "nuxt-session",
|
|
57
|
-
password: "",
|
|
53
|
+
password: process.env.NUXT_SESSION_PASSWORD || "",
|
|
58
54
|
cookie: {
|
|
59
55
|
sameSite: "lax"
|
|
60
56
|
}
|
|
61
57
|
});
|
|
58
|
+
if (nuxt.options.dev && !runtimeConfig.session.password) {
|
|
59
|
+
runtimeConfig.session.password = randomUUID().replace(/-/g, "");
|
|
60
|
+
const envPath = join(nuxt.options.rootDir, ".env");
|
|
61
|
+
const envContent = await readFile(envPath, "utf-8").catch(() => "");
|
|
62
|
+
if (!envContent.includes("NUXT_SESSION_PASSWORD")) {
|
|
63
|
+
await writeFile(envPath, `${envContent ? envContent + "\n" : envContent}NUXT_SESSION_PASSWORD=${runtimeConfig.session.password}`, "utf-8");
|
|
64
|
+
}
|
|
65
|
+
} else if (!nuxt.options._prepare && !runtimeConfig.session.password) {
|
|
66
|
+
throw new Error("NUXT_SESSION_PASSWORD environment variable or runtimeConfig.session.password not set");
|
|
67
|
+
}
|
|
62
68
|
runtimeConfig.oauth = defu(runtimeConfig.oauth, {});
|
|
63
69
|
runtimeConfig.oauth.github = defu(runtimeConfig.oauth.github, {
|
|
64
70
|
clientId: "",
|
|
@@ -1,10 +1,2 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
user: any;
|
|
4
|
-
session: any;
|
|
5
|
-
fetch: typeof fetch;
|
|
6
|
-
clear: typeof clear;
|
|
7
|
-
};
|
|
8
|
-
declare function fetch(): Promise<void>;
|
|
9
|
-
declare function clear(): Promise<void>;
|
|
10
|
-
export {};
|
|
1
|
+
import type { UserSessionComposable } from '#auth-utils';
|
|
2
|
+
export declare function useUserSession(): UserSessionComposable;
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { useState, computed, useRequestFetch } from "#imports";
|
|
2
2
|
const useSessionState = () => useState("nuxt-session", () => ({}));
|
|
3
|
-
export
|
|
3
|
+
export function useUserSession() {
|
|
4
4
|
const sessionState = useSessionState();
|
|
5
5
|
return {
|
|
6
6
|
loggedIn: computed(() => Boolean(sessionState.value.user)),
|
|
@@ -9,7 +9,7 @@ export const useUserSession = () => {
|
|
|
9
9
|
fetch,
|
|
10
10
|
clear
|
|
11
11
|
};
|
|
12
|
-
}
|
|
12
|
+
}
|
|
13
13
|
async function fetch() {
|
|
14
14
|
useSessionState().value = await useRequestFetch()("/api/_auth/session", {
|
|
15
15
|
headers: {
|
|
@@ -45,5 +45,11 @@ export interface OAuthAuth0Config {
|
|
|
45
45
|
* @example 'github'
|
|
46
46
|
*/
|
|
47
47
|
connection?: string;
|
|
48
|
+
/**
|
|
49
|
+
* Extra authorization parameters to provide to the authorization URL
|
|
50
|
+
* @see https://auth0.com/docs/api/authentication#social
|
|
51
|
+
* @example { display: 'popup' }
|
|
52
|
+
*/
|
|
53
|
+
authorizationParams?: Record<string, string>;
|
|
48
54
|
}
|
|
49
55
|
export declare function auth0EventHandler({ config, onSuccess, onError }: OAuthConfig<OAuthAuth0Config>): import("h3").EventHandler<import("h3").EventHandlerRequest, Promise<any>>;
|
|
@@ -5,7 +5,9 @@ import { defu } from "defu";
|
|
|
5
5
|
import { useRuntimeConfig } from "#imports";
|
|
6
6
|
export function auth0EventHandler({ config, onSuccess, onError }) {
|
|
7
7
|
return eventHandler(async (event) => {
|
|
8
|
-
config = defu(config, useRuntimeConfig(event).oauth?.auth0
|
|
8
|
+
config = defu(config, useRuntimeConfig(event).oauth?.auth0, {
|
|
9
|
+
authorizationParams: {}
|
|
10
|
+
});
|
|
9
11
|
const { code } = getQuery(event);
|
|
10
12
|
if (!config.clientId || !config.clientSecret || !config.domain) {
|
|
11
13
|
const error = createError({
|
|
@@ -33,7 +35,8 @@ export function auth0EventHandler({ config, onSuccess, onError }) {
|
|
|
33
35
|
scope: config.scope.join(" "),
|
|
34
36
|
audience: config.audience || "",
|
|
35
37
|
max_age: config.maxAge || 0,
|
|
36
|
-
connection: config.connection || ""
|
|
38
|
+
connection: config.connection || "",
|
|
39
|
+
...config.authorizationParams
|
|
37
40
|
})
|
|
38
41
|
);
|
|
39
42
|
}
|
|
@@ -34,5 +34,10 @@ export interface OAuthBattledotnetConfig {
|
|
|
34
34
|
* @default 'https://oauth.battle.net/token'
|
|
35
35
|
*/
|
|
36
36
|
tokenURL?: string;
|
|
37
|
+
/**
|
|
38
|
+
* Extra authorization parameters to provide to the authorization URL
|
|
39
|
+
* @see https://develop.battle.net/documentation/guides/using-oauth/authorization-code-flow
|
|
40
|
+
*/
|
|
41
|
+
authorizationParams?: Record<string, string>;
|
|
37
42
|
}
|
|
38
43
|
export declare function battledotnetEventHandler({ config, onSuccess, onError }: OAuthConfig<OAuthBattledotnetConfig>): import("h3").EventHandler<import("h3").EventHandlerRequest, Promise<any>>;
|
|
@@ -8,7 +8,8 @@ export function battledotnetEventHandler({ config, onSuccess, onError }) {
|
|
|
8
8
|
return eventHandler(async (event) => {
|
|
9
9
|
config = defu(config, useRuntimeConfig(event).oauth?.battledotnet, {
|
|
10
10
|
authorizationURL: "https://oauth.battle.net/authorize",
|
|
11
|
-
tokenURL: "https://oauth.battle.net/token"
|
|
11
|
+
tokenURL: "https://oauth.battle.net/token",
|
|
12
|
+
authorizationParams: {}
|
|
12
13
|
});
|
|
13
14
|
const query = getQuery(event);
|
|
14
15
|
const { code } = query;
|
|
@@ -47,7 +48,8 @@ export function battledotnetEventHandler({ config, onSuccess, onError }) {
|
|
|
47
48
|
scope: config.scope.join(" "),
|
|
48
49
|
state: randomUUID(),
|
|
49
50
|
// Todo: handle PKCE flow
|
|
50
|
-
response_type: "code"
|
|
51
|
+
response_type: "code",
|
|
52
|
+
...config.authorizationParams
|
|
51
53
|
})
|
|
52
54
|
);
|
|
53
55
|
}
|
|
@@ -25,5 +25,10 @@ export interface OAuthCognitoConfig {
|
|
|
25
25
|
* @default []
|
|
26
26
|
*/
|
|
27
27
|
scope?: string[];
|
|
28
|
+
/**
|
|
29
|
+
* Extra authorization parameters to provide to the authorization URL
|
|
30
|
+
* @see https://docs.aws.amazon.com/cognito/latest/developerguide/authorization-endpoint.html
|
|
31
|
+
*/
|
|
32
|
+
authorizationParams?: Record<string, string>;
|
|
28
33
|
}
|
|
29
34
|
export declare function cognitoEventHandler({ config, onSuccess, onError }: OAuthConfig<OAuthCognitoConfig>): import("h3").EventHandler<import("h3").EventHandlerRequest, Promise<any>>;
|
|
@@ -5,7 +5,9 @@ import { defu } from "defu";
|
|
|
5
5
|
import { useRuntimeConfig } from "#imports";
|
|
6
6
|
export function cognitoEventHandler({ config, onSuccess, onError }) {
|
|
7
7
|
return eventHandler(async (event) => {
|
|
8
|
-
config = defu(config, useRuntimeConfig(event).oauth?.cognito
|
|
8
|
+
config = defu(config, useRuntimeConfig(event).oauth?.cognito, {
|
|
9
|
+
authorizationParams: {}
|
|
10
|
+
});
|
|
9
11
|
const { code } = getQuery(event);
|
|
10
12
|
if (!config.clientId || !config.clientSecret || !config.userPoolId || !config.region) {
|
|
11
13
|
const error = createError({
|
|
@@ -27,7 +29,8 @@ export function cognitoEventHandler({ config, onSuccess, onError }) {
|
|
|
27
29
|
client_id: config.clientId,
|
|
28
30
|
redirect_uri: redirectUrl,
|
|
29
31
|
response_type: "code",
|
|
30
|
-
scope: config.scope.join(" ")
|
|
32
|
+
scope: config.scope.join(" "),
|
|
33
|
+
...config.authorizationParams
|
|
31
34
|
})
|
|
32
35
|
);
|
|
33
36
|
}
|
|
@@ -38,5 +38,11 @@ export interface OAuthDiscordConfig {
|
|
|
38
38
|
* @default 'https://discord.com/api/oauth2/token'
|
|
39
39
|
*/
|
|
40
40
|
tokenURL?: string;
|
|
41
|
+
/**
|
|
42
|
+
* Extra authorization parameters to provide to the authorization URL
|
|
43
|
+
* @see 'https://discord.com/developers/docs/topics/oauth2#authorization-code-grant'
|
|
44
|
+
* @example { allow_signup: 'true' }
|
|
45
|
+
*/
|
|
46
|
+
authorizationParams?: Record<string, string>;
|
|
41
47
|
}
|
|
42
48
|
export declare function discordEventHandler({ config, onSuccess, onError }: OAuthConfig<OAuthDiscordConfig>): import("h3").EventHandler<import("h3").EventHandlerRequest, Promise<any>>;
|
|
@@ -8,7 +8,8 @@ export function discordEventHandler({ config, onSuccess, onError }) {
|
|
|
8
8
|
config = defu(config, useRuntimeConfig(event).oauth?.discord, {
|
|
9
9
|
authorizationURL: "https://discord.com/oauth2/authorize",
|
|
10
10
|
tokenURL: "https://discord.com/api/oauth2/token",
|
|
11
|
-
profileRequired: true
|
|
11
|
+
profileRequired: true,
|
|
12
|
+
authorizationParams: {}
|
|
12
13
|
});
|
|
13
14
|
const { code } = getQuery(event);
|
|
14
15
|
if (!config.clientId || !config.clientSecret) {
|
|
@@ -35,7 +36,8 @@ export function discordEventHandler({ config, onSuccess, onError }) {
|
|
|
35
36
|
response_type: "code",
|
|
36
37
|
client_id: config.clientId,
|
|
37
38
|
redirect_uri: redirectUrl,
|
|
38
|
-
scope: config.scope.join(" ")
|
|
39
|
+
scope: config.scope.join(" "),
|
|
40
|
+
...config.authorizationParams
|
|
39
41
|
})
|
|
40
42
|
);
|
|
41
43
|
}
|
|
@@ -32,5 +32,11 @@ export interface OAuthGitHubConfig {
|
|
|
32
32
|
* @default 'https://github.com/login/oauth/access_token'
|
|
33
33
|
*/
|
|
34
34
|
tokenURL?: string;
|
|
35
|
+
/**
|
|
36
|
+
* Extra authorization parameters to provide to the authorization URL
|
|
37
|
+
* @see https://docs.github.com/en/apps/oauth-apps/building-oauth-apps/authorizing-oauth-apps#1-request-a-users-github-identity
|
|
38
|
+
* @example { allow_signup: 'true' }
|
|
39
|
+
*/
|
|
40
|
+
authorizationParams?: Record<string, string>;
|
|
35
41
|
}
|
|
36
42
|
export declare function githubEventHandler({ config, onSuccess, onError }: OAuthConfig<OAuthGitHubConfig>): import("h3").EventHandler<import("h3").EventHandlerRequest, Promise<any>>;
|
|
@@ -7,9 +7,20 @@ export function githubEventHandler({ config, onSuccess, onError }) {
|
|
|
7
7
|
return eventHandler(async (event) => {
|
|
8
8
|
config = defu(config, useRuntimeConfig(event).oauth?.github, {
|
|
9
9
|
authorizationURL: "https://github.com/login/oauth/authorize",
|
|
10
|
-
tokenURL: "https://github.com/login/oauth/access_token"
|
|
10
|
+
tokenURL: "https://github.com/login/oauth/access_token",
|
|
11
|
+
authorizationParams: {}
|
|
11
12
|
});
|
|
12
|
-
const
|
|
13
|
+
const query = getQuery(event);
|
|
14
|
+
if (query.error) {
|
|
15
|
+
const error = createError({
|
|
16
|
+
statusCode: 401,
|
|
17
|
+
message: `GitHub login failed: ${query.error || "Unknown error"}`,
|
|
18
|
+
data: query
|
|
19
|
+
});
|
|
20
|
+
if (!onError)
|
|
21
|
+
throw error;
|
|
22
|
+
return onError(event, error);
|
|
23
|
+
}
|
|
13
24
|
if (!config.clientId || !config.clientSecret) {
|
|
14
25
|
const error = createError({
|
|
15
26
|
statusCode: 500,
|
|
@@ -19,7 +30,7 @@ export function githubEventHandler({ config, onSuccess, onError }) {
|
|
|
19
30
|
throw error;
|
|
20
31
|
return onError(event, error);
|
|
21
32
|
}
|
|
22
|
-
if (!code) {
|
|
33
|
+
if (!query.code) {
|
|
23
34
|
config.scope = config.scope || [];
|
|
24
35
|
if (config.emailRequired && !config.scope.includes("user:email")) {
|
|
25
36
|
config.scope.push("user:email");
|
|
@@ -30,7 +41,8 @@ export function githubEventHandler({ config, onSuccess, onError }) {
|
|
|
30
41
|
withQuery(config.authorizationURL, {
|
|
31
42
|
client_id: config.clientId,
|
|
32
43
|
redirect_uri: redirectUrl,
|
|
33
|
-
scope: config.scope.join(" ")
|
|
44
|
+
scope: config.scope.join(" "),
|
|
45
|
+
...config.authorizationParams
|
|
34
46
|
})
|
|
35
47
|
);
|
|
36
48
|
}
|
|
@@ -41,7 +53,7 @@ export function githubEventHandler({ config, onSuccess, onError }) {
|
|
|
41
53
|
body: {
|
|
42
54
|
client_id: config.clientId,
|
|
43
55
|
client_secret: config.clientSecret,
|
|
44
|
-
code
|
|
56
|
+
code: query.code
|
|
45
57
|
}
|
|
46
58
|
}
|
|
47
59
|
);
|
|
@@ -27,5 +27,11 @@ export interface OAuthGoogleConfig {
|
|
|
27
27
|
* @default 'https://oauth2.googleapis.com/token'
|
|
28
28
|
*/
|
|
29
29
|
tokenURL?: string;
|
|
30
|
+
/**
|
|
31
|
+
* Extra authorization parameters to provide to the authorization URL
|
|
32
|
+
* @see https://developers.google.com/identity/protocols/oauth2/web-server#httprest_3
|
|
33
|
+
* @example { access_type: 'offline' }
|
|
34
|
+
*/
|
|
35
|
+
authorizationParams?: Record<string, string>;
|
|
30
36
|
}
|
|
31
37
|
export declare function googleEventHandler({ config, onSuccess, onError, }: OAuthConfig<OAuthGoogleConfig>): import("h3").EventHandler<import("h3").EventHandlerRequest, Promise<any>>;
|
|
@@ -17,7 +17,8 @@ export function googleEventHandler({
|
|
|
17
17
|
return eventHandler(async (event) => {
|
|
18
18
|
config = defu(config, useRuntimeConfig(event).oauth?.google, {
|
|
19
19
|
authorizationURL: "https://accounts.google.com/o/oauth2/v2/auth",
|
|
20
|
-
tokenURL: "https://oauth2.googleapis.com/token"
|
|
20
|
+
tokenURL: "https://oauth2.googleapis.com/token",
|
|
21
|
+
authorizationParams: {}
|
|
21
22
|
});
|
|
22
23
|
const { code } = getQuery(event);
|
|
23
24
|
if (!config.clientId) {
|
|
@@ -38,7 +39,8 @@ export function googleEventHandler({
|
|
|
38
39
|
response_type: "code",
|
|
39
40
|
client_id: config.clientId,
|
|
40
41
|
redirect_uri: redirectUrl,
|
|
41
|
-
scope: config.scope.join(" ")
|
|
42
|
+
scope: config.scope.join(" "),
|
|
43
|
+
...config.authorizationParams
|
|
42
44
|
})
|
|
43
45
|
);
|
|
44
46
|
}
|
|
@@ -28,5 +28,9 @@ export interface OAuthKeycloakConfig {
|
|
|
28
28
|
* @example ['openid']
|
|
29
29
|
*/
|
|
30
30
|
scope?: string[];
|
|
31
|
+
/**
|
|
32
|
+
* Extra authorization parameters to provide to the authorization URL
|
|
33
|
+
*/
|
|
34
|
+
authorizationParams?: Record<string, string>;
|
|
31
35
|
}
|
|
32
36
|
export declare function keycloakEventHandler({ config, onSuccess, onError, }: OAuthConfig<OAuthKeycloakConfig>): import("h3").EventHandler<import("h3").EventHandlerRequest, Promise<any>>;
|
|
@@ -15,11 +15,9 @@ export function keycloakEventHandler({
|
|
|
15
15
|
onError
|
|
16
16
|
}) {
|
|
17
17
|
return eventHandler(async (event) => {
|
|
18
|
-
config = defu(
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
useRuntimeConfig(event).oauth?.keycloak
|
|
22
|
-
);
|
|
18
|
+
config = defu(config, useRuntimeConfig(event).oauth?.keycloak, {
|
|
19
|
+
authorizationParams: {}
|
|
20
|
+
});
|
|
23
21
|
const query = getQuery(event);
|
|
24
22
|
const { code } = query;
|
|
25
23
|
if (query.error) {
|
|
@@ -53,7 +51,8 @@ export function keycloakEventHandler({
|
|
|
53
51
|
client_id: config.clientId,
|
|
54
52
|
redirect_uri: redirectUrl,
|
|
55
53
|
scope: config.scope.join(" "),
|
|
56
|
-
response_type: "code"
|
|
54
|
+
response_type: "code",
|
|
55
|
+
...config.authorizationParams
|
|
57
56
|
})
|
|
58
57
|
);
|
|
59
58
|
}
|
|
@@ -31,6 +31,11 @@ export interface OAuthLinkedInConfig {
|
|
|
31
31
|
* @default 'https://www.linkedin.com/oauth/v2/accessToken'
|
|
32
32
|
*/
|
|
33
33
|
tokenURL?: string;
|
|
34
|
+
/**
|
|
35
|
+
* Extra authorization parameters to provide to the authorization URL
|
|
36
|
+
* @see https://docs.microsoft.com/en-us/linkedin/shared/authentication/authorization-code-flow?context=linkedin/context
|
|
37
|
+
*/
|
|
38
|
+
authorizationParams?: Record<string, string>;
|
|
34
39
|
}
|
|
35
40
|
interface OAuthConfig {
|
|
36
41
|
config?: OAuthLinkedInConfig;
|
|
@@ -7,7 +7,8 @@ export function linkedinEventHandler({ config, onSuccess, onError }) {
|
|
|
7
7
|
return eventHandler(async (event) => {
|
|
8
8
|
config = defu(config, useRuntimeConfig(event).oauth?.linkedin, {
|
|
9
9
|
authorizationURL: "https://www.linkedin.com/oauth/v2/authorization",
|
|
10
|
-
tokenURL: "https://www.linkedin.com/oauth/v2/accessToken"
|
|
10
|
+
tokenURL: "https://www.linkedin.com/oauth/v2/accessToken",
|
|
11
|
+
authorizationParams: {}
|
|
11
12
|
});
|
|
12
13
|
const { code } = getQuery(event);
|
|
13
14
|
if (!config.clientId || !config.clientSecret) {
|
|
@@ -34,7 +35,8 @@ export function linkedinEventHandler({ config, onSuccess, onError }) {
|
|
|
34
35
|
response_type: "code",
|
|
35
36
|
client_id: config.clientId,
|
|
36
37
|
redirect_uri: redirectUrl,
|
|
37
|
-
scope: config.scope.join(" ")
|
|
38
|
+
scope: config.scope.join(" "),
|
|
39
|
+
...config.authorizationParams
|
|
38
40
|
})
|
|
39
41
|
);
|
|
40
42
|
}
|
|
@@ -23,22 +23,27 @@ export interface OAuthMicrosoftConfig {
|
|
|
23
23
|
scope?: string[];
|
|
24
24
|
/**
|
|
25
25
|
* Microsoft OAuth Authorization URL
|
|
26
|
-
* @default https://login.microsoftonline.com/${tenant}/oauth2/v2.0/authorize
|
|
26
|
+
* @default 'https://login.microsoftonline.com/${tenant}/oauth2/v2.0/authorize'
|
|
27
27
|
* @see https://docs.microsoft.com/en-us/azure/active-directory/develop/v2-oauth2-auth-code-flow
|
|
28
28
|
*/
|
|
29
29
|
authorizationURL?: string;
|
|
30
30
|
/**
|
|
31
31
|
* Microsoft OAuth Token URL
|
|
32
|
-
* @default https://login.microsoftonline.com/${tenant}/oauth2/v2.0/token
|
|
32
|
+
* @default 'https://login.microsoftonline.com/${tenant}/oauth2/v2.0/token'
|
|
33
33
|
* @see https://docs.microsoft.com/en-us/azure/active-directory/develop/v2-oauth2-auth-code-flow
|
|
34
34
|
*/
|
|
35
35
|
tokenURL?: string;
|
|
36
36
|
/**
|
|
37
37
|
* Microsoft OAuth User URL
|
|
38
|
-
* @default https://graph.microsoft.com/v1.0/me
|
|
38
|
+
* @default 'https://graph.microsoft.com/v1.0/me'
|
|
39
39
|
* @see https://docs.microsoft.com/en-us/graph/api/user-get?view=graph-rest-1.0&tabs=http
|
|
40
40
|
*/
|
|
41
41
|
userURL?: string;
|
|
42
|
+
/**
|
|
43
|
+
* Extra authorization parameters to provide to the authorization URL
|
|
44
|
+
* @see https://docs.microsoft.com/en-us/azure/active-directory/develop/v2-oauth2-auth-code-flow
|
|
45
|
+
*/
|
|
46
|
+
authorizationParams?: Record<string, string>;
|
|
42
47
|
}
|
|
43
48
|
interface OAuthConfig {
|
|
44
49
|
config?: OAuthMicrosoftConfig;
|
|
@@ -5,7 +5,9 @@ import { defu } from "defu";
|
|
|
5
5
|
import { useRuntimeConfig } from "#imports";
|
|
6
6
|
export function microsoftEventHandler({ config, onSuccess, onError }) {
|
|
7
7
|
return eventHandler(async (event) => {
|
|
8
|
-
config = defu(config, useRuntimeConfig(event).oauth?.microsoft
|
|
8
|
+
config = defu(config, useRuntimeConfig(event).oauth?.microsoft, {
|
|
9
|
+
authorizationParams: {}
|
|
10
|
+
});
|
|
9
11
|
const { code } = getQuery(event);
|
|
10
12
|
if (!config.clientId || !config.clientSecret || !config.tenant) {
|
|
11
13
|
const error = createError({
|
|
@@ -27,7 +29,8 @@ export function microsoftEventHandler({ config, onSuccess, onError }) {
|
|
|
27
29
|
client_id: config.clientId,
|
|
28
30
|
response_type: "code",
|
|
29
31
|
redirect_uri: redirectUrl,
|
|
30
|
-
scope: scope.join(" ")
|
|
32
|
+
scope: scope.join(" "),
|
|
33
|
+
...config.authorizationParams
|
|
31
34
|
})
|
|
32
35
|
);
|
|
33
36
|
}
|
|
@@ -32,5 +32,11 @@ export interface OAuthSpotifyConfig {
|
|
|
32
32
|
* @default 'https://accounts.spotify.com/api/token'
|
|
33
33
|
*/
|
|
34
34
|
tokenURL?: string;
|
|
35
|
+
/**
|
|
36
|
+
* Extra authorization parameters to provide to the authorization URL
|
|
37
|
+
* @see 'https://developer.spotify.com/documentation/web-api/tutorials/code-flow'
|
|
38
|
+
* @example { show_dialog: 'true' }
|
|
39
|
+
*/
|
|
40
|
+
authorizationParams?: Record<string, string>;
|
|
35
41
|
}
|
|
36
42
|
export declare function spotifyEventHandler({ config, onSuccess, onError }: OAuthConfig<OAuthSpotifyConfig>): import("h3").EventHandler<import("h3").EventHandlerRequest, Promise<any>>;
|
|
@@ -7,7 +7,8 @@ export function spotifyEventHandler({ config, onSuccess, onError }) {
|
|
|
7
7
|
return eventHandler(async (event) => {
|
|
8
8
|
config = defu(config, useRuntimeConfig(event).oauth?.spotify, {
|
|
9
9
|
authorizationURL: "https://accounts.spotify.com/authorize",
|
|
10
|
-
tokenURL: "https://accounts.spotify.com/api/token"
|
|
10
|
+
tokenURL: "https://accounts.spotify.com/api/token",
|
|
11
|
+
authorizationParams: {}
|
|
11
12
|
});
|
|
12
13
|
const { code } = getQuery(event);
|
|
13
14
|
if (!config.clientId || !config.clientSecret) {
|
|
@@ -31,7 +32,8 @@ export function spotifyEventHandler({ config, onSuccess, onError }) {
|
|
|
31
32
|
response_type: "code",
|
|
32
33
|
client_id: config.clientId,
|
|
33
34
|
redirect_uri: redirectUrl,
|
|
34
|
-
scope: config.scope.join(" ")
|
|
35
|
+
scope: config.scope.join(" "),
|
|
36
|
+
...config.authorizationParams
|
|
35
37
|
})
|
|
36
38
|
);
|
|
37
39
|
}
|
|
@@ -32,5 +32,11 @@ export interface OAuthTwitchConfig {
|
|
|
32
32
|
* @default 'https://id.twitch.tv/oauth2/token'
|
|
33
33
|
*/
|
|
34
34
|
tokenURL?: string;
|
|
35
|
+
/**
|
|
36
|
+
* Extra authorization parameters to provide to the authorization URL
|
|
37
|
+
* @see https://dev.twitch.tv/docs/authentication/getting-tokens-oauth/#authorization-code-grant-flow
|
|
38
|
+
* @example { force_verify: 'true' }
|
|
39
|
+
*/
|
|
40
|
+
authorizationParams?: Record<string, string>;
|
|
35
41
|
}
|
|
36
42
|
export declare function twitchEventHandler({ config, onSuccess, onError }: OAuthConfig<OAuthTwitchConfig>): import("h3").EventHandler<import("h3").EventHandlerRequest, Promise<any>>;
|
|
@@ -7,7 +7,8 @@ export function twitchEventHandler({ config, onSuccess, onError }) {
|
|
|
7
7
|
return eventHandler(async (event) => {
|
|
8
8
|
config = defu(config, useRuntimeConfig(event).oauth?.twitch, {
|
|
9
9
|
authorizationURL: "https://id.twitch.tv/oauth2/authorize",
|
|
10
|
-
tokenURL: "https://id.twitch.tv/oauth2/token"
|
|
10
|
+
tokenURL: "https://id.twitch.tv/oauth2/token",
|
|
11
|
+
authorizationParams: {}
|
|
11
12
|
});
|
|
12
13
|
const { code } = getQuery(event);
|
|
13
14
|
if (!config.clientId) {
|
|
@@ -31,7 +32,8 @@ export function twitchEventHandler({ config, onSuccess, onError }) {
|
|
|
31
32
|
response_type: "code",
|
|
32
33
|
client_id: config.clientId,
|
|
33
34
|
redirect_uri: redirectUrl,
|
|
34
|
-
scope: config.scope.join(" ")
|
|
35
|
+
scope: config.scope.join(" "),
|
|
36
|
+
...config.authorizationParams
|
|
35
37
|
})
|
|
36
38
|
);
|
|
37
39
|
}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import type { H3Event } from 'h3';
|
|
2
|
-
import type { UserSession } from '#auth-utils';
|
|
2
|
+
import type { User, UserSession } from '#auth-utils';
|
|
3
3
|
export interface SessionHooks {
|
|
4
4
|
/**
|
|
5
5
|
* Called when fetching the session from the API
|
|
@@ -27,4 +27,6 @@ export declare function setUserSession(event: H3Event, data: UserSession): Promi
|
|
|
27
27
|
*/
|
|
28
28
|
export declare function replaceUserSession(event: H3Event, data: UserSession): Promise<UserSession>;
|
|
29
29
|
export declare function clearUserSession(event: H3Event): Promise<boolean>;
|
|
30
|
-
export declare function requireUserSession(event: H3Event): Promise<
|
|
30
|
+
export declare function requireUserSession(event: H3Event): Promise<UserSession & {
|
|
31
|
+
user: User;
|
|
32
|
+
}>;
|
|
@@ -33,10 +33,7 @@ export async function requireUserSession(event) {
|
|
|
33
33
|
}
|
|
34
34
|
return userSession;
|
|
35
35
|
}
|
|
36
|
-
|
|
36
|
+
const sessionConfig = useRuntimeConfig().session;
|
|
37
37
|
function _useSession(event) {
|
|
38
|
-
if (!sessionConfig) {
|
|
39
|
-
sessionConfig = defu({ password: process.env.NUXT_SESSION_PASSWORD }, useRuntimeConfig(event).session);
|
|
40
|
-
}
|
|
41
38
|
return useSession(event, sessionConfig);
|
|
42
39
|
}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
export type { UserSession,
|
|
1
|
+
export type { User, UserSession, UserSessionComposable } from './session';
|
|
2
2
|
export type { OAuthConfig } from './oauth-config';
|
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
import type { H3Event, H3Error } from 'h3';
|
|
2
|
-
|
|
3
|
-
export interface OAuthConfig<TConfig, TUser = UserSession, TTokens = any> {
|
|
2
|
+
export interface OAuthConfig<TConfig, TUser = any, TTokens = any> {
|
|
4
3
|
config?: TConfig;
|
|
5
4
|
onSuccess: (event: H3Event, result: {
|
|
6
5
|
user: TUser;
|
|
@@ -1,5 +1,13 @@
|
|
|
1
|
+
import type { ComputedRef, Ref } from 'vue';
|
|
1
2
|
export interface User {
|
|
2
3
|
}
|
|
3
4
|
export interface UserSession {
|
|
4
5
|
user?: User;
|
|
5
6
|
}
|
|
7
|
+
export interface UserSessionComposable {
|
|
8
|
+
loggedIn: ComputedRef<boolean>;
|
|
9
|
+
user: ComputedRef<User | null>;
|
|
10
|
+
session: Ref<UserSession>;
|
|
11
|
+
fetch: () => Promise<void>;
|
|
12
|
+
clear: () => Promise<void>;
|
|
13
|
+
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "nuxt-auth-utils",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.19",
|
|
4
4
|
"description": "Minimalist Auth module for Nuxt with SSR",
|
|
5
5
|
"repository": "Atinux/nuxt-auth-utils",
|
|
6
6
|
"license": "MIT",
|
|
@@ -34,7 +34,9 @@
|
|
|
34
34
|
"defu": "^6.1.4",
|
|
35
35
|
"hookable": "^5.5.3",
|
|
36
36
|
"ofetch": "^1.3.3",
|
|
37
|
-
"ohash": "^1.1.3"
|
|
37
|
+
"ohash": "^1.1.3",
|
|
38
|
+
"pathe": "^1.1.2",
|
|
39
|
+
"uncrypto": "^0.1.3"
|
|
38
40
|
},
|
|
39
41
|
"devDependencies": {
|
|
40
42
|
"@iconify-json/simple-icons": "^1.1.91",
|