@choiceform/shared-auth 0.1.17 → 0.1.18
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 +286 -134
- package/dist/__tests__/auth-utils.test.d.ts +5 -0
- package/dist/__tests__/auth-utils.test.d.ts.map +1 -0
- package/dist/__tests__/auth-utils.test.js +96 -0
- package/dist/__tests__/store.test.d.ts +5 -0
- package/dist/__tests__/store.test.d.ts.map +1 -0
- package/dist/__tests__/store.test.js +210 -0
- package/dist/__tests__/user-mapper.test.d.ts +5 -0
- package/dist/__tests__/user-mapper.test.d.ts.map +1 -0
- package/dist/__tests__/user-mapper.test.js +76 -0
- package/dist/api/auth-api.d.ts +93 -9
- package/dist/api/auth-api.d.ts.map +1 -1
- package/dist/api/auth-api.js +219 -80
- package/dist/api/client.d.ts +10 -0
- package/dist/api/client.d.ts.map +1 -1
- package/dist/api/client.js +10 -0
- package/dist/api/organization-api.d.ts +2 -7
- package/dist/api/organization-api.d.ts.map +1 -1
- package/dist/api/organization-api.js +2 -17
- package/dist/api/team-api.d.ts +1 -5
- package/dist/api/team-api.d.ts.map +1 -1
- package/dist/api/team-api.js +5 -11
- package/dist/components/auth-sync.d.ts +27 -0
- package/dist/components/auth-sync.d.ts.map +1 -0
- package/dist/components/auth-sync.js +117 -0
- package/dist/components/protected-route.d.ts +18 -0
- package/dist/components/protected-route.d.ts.map +1 -0
- package/dist/components/protected-route.js +34 -0
- package/dist/components/sign-in-page.d.ts +21 -0
- package/dist/components/sign-in-page.d.ts.map +1 -0
- package/dist/components/sign-in-page.js +31 -0
- package/dist/config.js +1 -1
- package/dist/core.d.ts +148 -71
- package/dist/core.d.ts.map +1 -1
- package/dist/core.js +109 -28
- package/dist/hooks/index.d.ts +8 -0
- package/dist/hooks/index.d.ts.map +1 -0
- package/dist/hooks/index.js +7 -0
- package/dist/hooks/use-auth-init.d.ts +4 -0
- package/dist/hooks/use-auth-init.d.ts.map +1 -1
- package/dist/hooks/use-auth-init.js +16 -21
- package/dist/hooks/use-auth-sync.d.ts +60 -0
- package/dist/hooks/use-auth-sync.d.ts.map +1 -0
- package/dist/hooks/use-auth-sync.js +116 -0
- package/dist/hooks/use-email-verification.d.ts +85 -0
- package/dist/hooks/use-email-verification.d.ts.map +1 -0
- package/dist/hooks/use-email-verification.js +145 -0
- package/dist/hooks/use-protected-route.d.ts +67 -0
- package/dist/hooks/use-protected-route.d.ts.map +1 -0
- package/dist/hooks/use-protected-route.js +102 -0
- package/dist/index.d.ts +12 -6
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +43 -13
- package/dist/init.d.ts +127 -70
- package/dist/init.d.ts.map +1 -1
- package/dist/lib/auth-client.d.ts.map +1 -1
- package/dist/lib/auth-client.js +75 -2
- package/dist/services/auth-service.d.ts +101 -0
- package/dist/services/auth-service.d.ts.map +1 -0
- package/dist/services/auth-service.js +356 -0
- package/dist/services/callback-service.d.ts +33 -0
- package/dist/services/callback-service.d.ts.map +1 -0
- package/dist/services/callback-service.js +473 -0
- package/dist/services/companion-team.d.ts.map +1 -1
- package/dist/services/companion-team.js +41 -39
- package/dist/services/index.d.ts +2 -0
- package/dist/services/index.d.ts.map +1 -1
- package/dist/services/index.js +2 -0
- package/dist/store/actions.d.ts +54 -51
- package/dist/store/actions.d.ts.map +1 -1
- package/dist/store/actions.js +111 -243
- package/dist/store/computed.d.ts +72 -1
- package/dist/store/computed.d.ts.map +1 -1
- package/dist/store/computed.js +90 -3
- package/dist/store/index.d.ts +3 -3
- package/dist/store/index.d.ts.map +1 -1
- package/dist/store/index.js +2 -2
- package/dist/store/state.d.ts +10 -0
- package/dist/store/state.d.ts.map +1 -1
- package/dist/store/state.js +11 -1
- package/dist/store/utils.d.ts +3 -34
- package/dist/store/utils.d.ts.map +1 -1
- package/dist/store/utils.js +2 -22
- package/dist/types/auth.d.ts +106 -0
- package/dist/types/auth.d.ts.map +1 -1
- package/dist/types/callback.d.ts +35 -0
- package/dist/types/callback.d.ts.map +1 -0
- package/dist/types/callback.js +1 -0
- package/dist/types/index.d.ts +4 -3
- package/dist/types/index.d.ts.map +1 -1
- package/dist/types/organization.d.ts +19 -3
- package/dist/types/organization.d.ts.map +1 -1
- package/dist/types/team.d.ts +6 -2
- package/dist/types/team.d.ts.map +1 -1
- package/dist/types/user.d.ts +7 -3
- package/dist/types/user.d.ts.map +1 -1
- package/dist/utils/auth-utils.d.ts +60 -0
- package/dist/utils/auth-utils.d.ts.map +1 -0
- package/dist/utils/auth-utils.js +146 -0
- package/dist/utils/index.d.ts +1 -0
- package/dist/utils/index.d.ts.map +1 -1
- package/dist/utils/index.js +1 -0
- package/dist/utils/user-mapper.d.ts.map +1 -1
- package/dist/utils/user-mapper.js +2 -1
- package/package.json +10 -2
package/dist/store/actions.d.ts
CHANGED
|
@@ -1,85 +1,88 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
2
|
+
* 认证状态 Actions
|
|
3
|
+
*
|
|
4
|
+
* 只负责状态管理,不包含业务逻辑
|
|
5
|
+
* 业务逻辑在 services/auth-service.ts 中
|
|
3
6
|
*/
|
|
4
7
|
import type { Observable } from "@legendapp/state";
|
|
5
|
-
import type {
|
|
8
|
+
import type { AuthState, SessionUser } from "../types";
|
|
6
9
|
import type { TokenStorage } from "../api";
|
|
7
10
|
/**
|
|
8
|
-
*
|
|
11
|
+
* 创建状态管理 Actions
|
|
12
|
+
*
|
|
13
|
+
* 这些是纯粹的状态操作,不涉及 API 调用或业务逻辑
|
|
9
14
|
*/
|
|
10
|
-
export declare function
|
|
15
|
+
export declare function createStoreActions(authStore: Observable<AuthState>, tokenStorage: TokenStorage): {
|
|
11
16
|
/**
|
|
12
|
-
*
|
|
17
|
+
* 获取当前用户
|
|
13
18
|
*/
|
|
14
|
-
|
|
19
|
+
getUser(): SessionUser | null;
|
|
15
20
|
/**
|
|
16
|
-
*
|
|
21
|
+
* 获取当前用户 ID
|
|
17
22
|
*/
|
|
18
|
-
|
|
23
|
+
getUserId(): string | null;
|
|
19
24
|
/**
|
|
20
|
-
*
|
|
25
|
+
* 检查是否已认证
|
|
21
26
|
*/
|
|
22
|
-
|
|
27
|
+
isAuthenticated(): boolean;
|
|
28
|
+
/**
|
|
29
|
+
* 检查是否正在加载
|
|
30
|
+
*/
|
|
31
|
+
isLoading(): boolean;
|
|
32
|
+
/**
|
|
33
|
+
* 检查是否已加载完成
|
|
34
|
+
*/
|
|
35
|
+
isLoaded(): boolean;
|
|
36
|
+
/**
|
|
37
|
+
* 设置用户
|
|
38
|
+
*/
|
|
39
|
+
setUser(user: SessionUser | null): void;
|
|
40
|
+
/**
|
|
41
|
+
* 更新用户(合并)
|
|
42
|
+
*/
|
|
43
|
+
updateUser(updates: Partial<SessionUser>): void;
|
|
23
44
|
/**
|
|
24
45
|
* 设置加载状态
|
|
25
46
|
*/
|
|
26
47
|
setLoading(loading: boolean): void;
|
|
27
48
|
/**
|
|
28
|
-
*
|
|
49
|
+
* 设置已加载状态
|
|
29
50
|
*/
|
|
30
|
-
|
|
51
|
+
setLoaded(loaded: boolean): void;
|
|
31
52
|
/**
|
|
32
|
-
*
|
|
33
|
-
*
|
|
34
|
-
* 直接调用 better-auth 的 signIn.social,传入完整的回调 URL
|
|
35
|
-
*
|
|
36
|
-
* @param provider - OAuth 提供商(如 github)
|
|
37
|
-
* @param callbackURL - 登录成功后的完整回调 URL
|
|
38
|
-
* @param newUserCallbackURL - 新用户的回调 URL(可选)
|
|
39
|
-
* @param errorCallbackURL - 登录失败后的完整回调 URL(可选)
|
|
53
|
+
* 设置错误
|
|
40
54
|
*/
|
|
41
|
-
|
|
55
|
+
setError(error: string | null): void;
|
|
42
56
|
/**
|
|
43
|
-
*
|
|
44
|
-
*
|
|
45
|
-
* 发送 Magic Link 到用户邮箱
|
|
46
|
-
*
|
|
47
|
-
* @param email - 用户邮箱
|
|
48
|
-
* @param callbackURL - 登录成功后的完整回调 URL
|
|
49
|
-
* @param name - 用户名称(可选,用于新用户)
|
|
50
|
-
* @param newUserCallbackURL - 新用户的回调 URL(可选)
|
|
51
|
-
* @returns 是否发送成功
|
|
57
|
+
* 设置认证成功状态
|
|
52
58
|
*/
|
|
53
|
-
|
|
59
|
+
setAuthenticated(user: SessionUser): void;
|
|
54
60
|
/**
|
|
55
|
-
*
|
|
56
|
-
*
|
|
57
|
-
* @param email - 邮箱
|
|
58
|
-
* @param password - 密码
|
|
59
|
-
* @returns 是否登录成功
|
|
61
|
+
* 清除认证状态
|
|
60
62
|
*/
|
|
61
|
-
|
|
63
|
+
clearAuth(): void;
|
|
62
64
|
/**
|
|
63
|
-
*
|
|
64
|
-
*
|
|
65
|
-
* @param email - 邮箱
|
|
66
|
-
* @param password - 密码
|
|
67
|
-
* @param name - 用户名
|
|
68
|
-
* @returns 是否注册成功
|
|
65
|
+
* 处理未授权
|
|
69
66
|
*/
|
|
70
|
-
|
|
67
|
+
handleUnauthorized(): void;
|
|
71
68
|
/**
|
|
72
|
-
*
|
|
69
|
+
* 更新活跃组织 ID
|
|
73
70
|
*/
|
|
74
|
-
|
|
71
|
+
setActiveOrganizationId(organizationId: string | null | undefined): void;
|
|
75
72
|
/**
|
|
76
|
-
*
|
|
73
|
+
* 更新活跃团队 ID
|
|
77
74
|
*/
|
|
78
|
-
|
|
75
|
+
setActiveTeamId(teamId: string | null | undefined): void;
|
|
79
76
|
/**
|
|
80
|
-
*
|
|
77
|
+
* 初始化认证状态
|
|
81
78
|
*/
|
|
82
|
-
|
|
79
|
+
initialize(user: SessionUser | null, isLoaded: boolean): void;
|
|
83
80
|
};
|
|
84
|
-
export type
|
|
81
|
+
export type StoreActions = ReturnType<typeof createStoreActions>;
|
|
82
|
+
/**
|
|
83
|
+
* @deprecated 使用 createStoreActions 代替
|
|
84
|
+
* 保留此函数以保持向后兼容性
|
|
85
|
+
*/
|
|
86
|
+
export { createStoreActions as createAuthActions };
|
|
87
|
+
export type { StoreActions as AuthActions };
|
|
85
88
|
//# sourceMappingURL=actions.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"actions.d.ts","sourceRoot":"","sources":["../../src/store/actions.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"actions.d.ts","sourceRoot":"","sources":["../../src/store/actions.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAA;AAClD,OAAO,KAAK,EAAE,SAAS,EAAE,WAAW,EAAE,MAAM,UAAU,CAAA;AACtD,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,QAAQ,CAAA;AAE1C;;;;GAIG;AACH,wBAAgB,kBAAkB,CAChC,SAAS,EAAE,UAAU,CAAC,SAAS,CAAC,EAChC,YAAY,EAAE,YAAY;IAOxB;;OAEG;eACQ,WAAW,GAAG,IAAI;IAI7B;;OAEG;iBACU,MAAM,GAAG,IAAI;IAI1B;;OAEG;uBACgB,OAAO;IAI1B;;OAEG;iBACU,OAAO;IAIpB;;OAEG;gBACS,OAAO;IAQnB;;OAEG;kBACW,WAAW,GAAG,IAAI;IAKhC;;OAEG;wBACiB,OAAO,CAAC,WAAW,CAAC;IAOxC;;OAEG;wBACiB,OAAO;IAI3B;;OAEG;sBACe,OAAO;IAOzB;;OAEG;oBACa,MAAM,GAAG,IAAI;IAI7B;;OAEG;2BACoB,WAAW;IAQlC;;OAEG;;IASH;;OAEG;;IASH;;OAEG;4CACqC,MAAM,GAAG,IAAI,GAAG,SAAS;IAUjE;;OAEG;4BACqB,MAAM,GAAG,IAAI,GAAG,SAAS;IAcjD;;OAEG;qBACc,WAAW,GAAG,IAAI,YAAY,OAAO;EAWzD;AAED,MAAM,MAAM,YAAY,GAAG,UAAU,CAAC,OAAO,kBAAkB,CAAC,CAAA;AAMhE;;;GAGG;AACH,OAAO,EAAE,kBAAkB,IAAI,iBAAiB,EAAE,CAAA;AAClD,YAAY,EAAE,YAAY,IAAI,WAAW,EAAE,CAAA"}
|
package/dist/store/actions.js
CHANGED
|
@@ -1,91 +1,67 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
2
|
+
* 认证状态 Actions
|
|
3
|
+
*
|
|
4
|
+
* 只负责状态管理,不包含业务逻辑
|
|
5
|
+
* 业务逻辑在 services/auth-service.ts 中
|
|
3
6
|
*/
|
|
4
|
-
import { extractSessionUser } from "../utils";
|
|
5
7
|
/**
|
|
6
|
-
*
|
|
8
|
+
* 创建状态管理 Actions
|
|
9
|
+
*
|
|
10
|
+
* 这些是纯粹的状态操作,不涉及 API 调用或业务逻辑
|
|
7
11
|
*/
|
|
8
|
-
export function
|
|
9
|
-
const { baseURL, getSessionEndpoint = "/v1/auth/get-session", skipTokenCleanupOnError = false, } = config;
|
|
12
|
+
export function createStoreActions(authStore, tokenStorage) {
|
|
10
13
|
return {
|
|
14
|
+
// ============================================================
|
|
15
|
+
// 状态读取
|
|
16
|
+
// ============================================================
|
|
11
17
|
/**
|
|
12
|
-
*
|
|
18
|
+
* 获取当前用户
|
|
13
19
|
*/
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
if (!user && storedToken) {
|
|
17
|
-
await this.fetchSessionWithToken(storedToken);
|
|
18
|
-
}
|
|
19
|
-
else if (user) {
|
|
20
|
-
authStore.user.set(user);
|
|
21
|
-
authStore.isAuthenticated.set(true);
|
|
22
|
-
}
|
|
23
|
-
else {
|
|
24
|
-
authStore.user.set(null);
|
|
25
|
-
authStore.isAuthenticated.set(false);
|
|
26
|
-
}
|
|
27
|
-
authStore.isLoaded.set(isLoaded);
|
|
28
|
-
authStore.loading.set(!isLoaded);
|
|
20
|
+
getUser() {
|
|
21
|
+
return authStore.user.get();
|
|
29
22
|
},
|
|
30
23
|
/**
|
|
31
|
-
*
|
|
24
|
+
* 获取当前用户 ID
|
|
32
25
|
*/
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
if (!token) {
|
|
36
|
-
throw new Error("Token is required");
|
|
37
|
-
}
|
|
38
|
-
tokenStorage.save(token);
|
|
39
|
-
const endpoint = `${baseURL}${getSessionEndpoint}`;
|
|
40
|
-
const response = await fetch(endpoint, {
|
|
41
|
-
method: "GET",
|
|
42
|
-
headers: {
|
|
43
|
-
Authorization: `Bearer ${token}`,
|
|
44
|
-
"Content-Type": "application/json",
|
|
45
|
-
},
|
|
46
|
-
});
|
|
47
|
-
if (!response.ok) {
|
|
48
|
-
throw new Error(`Failed to fetch session: ${response.status}`);
|
|
49
|
-
}
|
|
50
|
-
const responseText = await response.text();
|
|
51
|
-
let sessionData = null;
|
|
52
|
-
try {
|
|
53
|
-
if (responseText && responseText !== "null" && responseText !== "") {
|
|
54
|
-
sessionData = JSON.parse(responseText);
|
|
55
|
-
}
|
|
56
|
-
}
|
|
57
|
-
catch {
|
|
58
|
-
this.handleUnauthorized();
|
|
59
|
-
return;
|
|
60
|
-
}
|
|
61
|
-
const userData = extractSessionUser(sessionData);
|
|
62
|
-
if (userData) {
|
|
63
|
-
authStore.user.set(userData);
|
|
64
|
-
authStore.isAuthenticated.set(true);
|
|
65
|
-
authStore.isLoaded.set(true);
|
|
66
|
-
authStore.loading.set(false);
|
|
67
|
-
}
|
|
68
|
-
else {
|
|
69
|
-
this.handleUnauthorized();
|
|
70
|
-
}
|
|
71
|
-
}
|
|
72
|
-
catch {
|
|
73
|
-
this.handleUnauthorized();
|
|
74
|
-
}
|
|
26
|
+
getUserId() {
|
|
27
|
+
return authStore.user.get()?.id ?? null;
|
|
75
28
|
},
|
|
76
29
|
/**
|
|
77
|
-
*
|
|
30
|
+
* 检查是否已认证
|
|
78
31
|
*/
|
|
79
|
-
|
|
80
|
-
authStore.
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
32
|
+
isAuthenticated() {
|
|
33
|
+
return authStore.isAuthenticated.get();
|
|
34
|
+
},
|
|
35
|
+
/**
|
|
36
|
+
* 检查是否正在加载
|
|
37
|
+
*/
|
|
38
|
+
isLoading() {
|
|
39
|
+
return authStore.loading.get();
|
|
40
|
+
},
|
|
41
|
+
/**
|
|
42
|
+
* 检查是否已加载完成
|
|
43
|
+
*/
|
|
44
|
+
isLoaded() {
|
|
45
|
+
return authStore.isLoaded.get();
|
|
46
|
+
},
|
|
47
|
+
// ============================================================
|
|
48
|
+
// 状态更新
|
|
49
|
+
// ============================================================
|
|
50
|
+
/**
|
|
51
|
+
* 设置用户
|
|
52
|
+
*/
|
|
53
|
+
setUser(user) {
|
|
54
|
+
authStore.user.set(user);
|
|
55
|
+
authStore.isAuthenticated.set(user !== null);
|
|
56
|
+
},
|
|
57
|
+
/**
|
|
58
|
+
* 更新用户(合并)
|
|
59
|
+
*/
|
|
60
|
+
updateUser(updates) {
|
|
61
|
+
const currentUser = authStore.user.get();
|
|
62
|
+
if (currentUser) {
|
|
63
|
+
authStore.user.set({ ...currentUser, ...updates });
|
|
87
64
|
}
|
|
88
|
-
tokenStorage.clear();
|
|
89
65
|
},
|
|
90
66
|
/**
|
|
91
67
|
* 设置加载状态
|
|
@@ -94,205 +70,97 @@ export function createAuthActions(authStore, tokenStorage, config, authClient) {
|
|
|
94
70
|
authStore.loading.set(loading);
|
|
95
71
|
},
|
|
96
72
|
/**
|
|
97
|
-
*
|
|
73
|
+
* 设置已加载状态
|
|
74
|
+
*/
|
|
75
|
+
setLoaded(loaded) {
|
|
76
|
+
authStore.isLoaded.set(loaded);
|
|
77
|
+
if (loaded) {
|
|
78
|
+
authStore.loading.set(false);
|
|
79
|
+
}
|
|
80
|
+
},
|
|
81
|
+
/**
|
|
82
|
+
* 设置错误
|
|
98
83
|
*/
|
|
99
84
|
setError(error) {
|
|
100
85
|
authStore.error.set(error);
|
|
101
86
|
},
|
|
102
87
|
/**
|
|
103
|
-
*
|
|
104
|
-
*
|
|
105
|
-
* 直接调用 better-auth 的 signIn.social,传入完整的回调 URL
|
|
106
|
-
*
|
|
107
|
-
* @param provider - OAuth 提供商(如 github)
|
|
108
|
-
* @param callbackURL - 登录成功后的完整回调 URL
|
|
109
|
-
* @param newUserCallbackURL - 新用户的回调 URL(可选)
|
|
110
|
-
* @param errorCallbackURL - 登录失败后的完整回调 URL(可选)
|
|
88
|
+
* 设置认证成功状态
|
|
111
89
|
*/
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
authStore.error.set(null);
|
|
119
|
-
await authClient.signIn.social({
|
|
120
|
-
provider,
|
|
121
|
-
callbackURL,
|
|
122
|
-
newUserCallbackURL,
|
|
123
|
-
errorCallbackURL,
|
|
124
|
-
});
|
|
125
|
-
}
|
|
126
|
-
catch (error) {
|
|
127
|
-
const message = error instanceof Error ? error.message : "Sign in failed";
|
|
128
|
-
authStore.error.set(message);
|
|
129
|
-
authStore.loading.set(false);
|
|
130
|
-
}
|
|
90
|
+
setAuthenticated(user) {
|
|
91
|
+
authStore.user.set(user);
|
|
92
|
+
authStore.isAuthenticated.set(true);
|
|
93
|
+
authStore.isLoaded.set(true);
|
|
94
|
+
authStore.loading.set(false);
|
|
95
|
+
authStore.error.set(null);
|
|
131
96
|
},
|
|
132
97
|
/**
|
|
133
|
-
*
|
|
134
|
-
*
|
|
135
|
-
* 发送 Magic Link 到用户邮箱
|
|
136
|
-
*
|
|
137
|
-
* @param email - 用户邮箱
|
|
138
|
-
* @param callbackURL - 登录成功后的完整回调 URL
|
|
139
|
-
* @param name - 用户名称(可选,用于新用户)
|
|
140
|
-
* @param newUserCallbackURL - 新用户的回调 URL(可选)
|
|
141
|
-
* @returns 是否发送成功
|
|
98
|
+
* 清除认证状态
|
|
142
99
|
*/
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
return false;
|
|
150
|
-
}
|
|
151
|
-
try {
|
|
152
|
-
authStore.loading.set(true);
|
|
153
|
-
authStore.error.set(null);
|
|
154
|
-
await authClient.signIn.magicLink({
|
|
155
|
-
email,
|
|
156
|
-
name,
|
|
157
|
-
callbackURL,
|
|
158
|
-
newUserCallbackURL,
|
|
159
|
-
});
|
|
160
|
-
authStore.loading.set(false);
|
|
161
|
-
return true;
|
|
162
|
-
}
|
|
163
|
-
catch (error) {
|
|
164
|
-
const message = error instanceof Error ? error.message : "Failed to send magic link";
|
|
165
|
-
authStore.error.set(message);
|
|
166
|
-
authStore.loading.set(false);
|
|
167
|
-
return false;
|
|
168
|
-
}
|
|
100
|
+
clearAuth() {
|
|
101
|
+
authStore.user.set(null);
|
|
102
|
+
authStore.isAuthenticated.set(false);
|
|
103
|
+
authStore.isLoaded.set(true);
|
|
104
|
+
authStore.loading.set(false);
|
|
105
|
+
tokenStorage.clear();
|
|
169
106
|
},
|
|
170
107
|
/**
|
|
171
|
-
*
|
|
172
|
-
*
|
|
173
|
-
* @param email - 邮箱
|
|
174
|
-
* @param password - 密码
|
|
175
|
-
* @returns 是否登录成功
|
|
108
|
+
* 处理未授权
|
|
176
109
|
*/
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
return false;
|
|
180
|
-
}
|
|
181
|
-
if (!authClient.signIn.email) {
|
|
182
|
-
authStore.error.set("Email sign in is not available.");
|
|
183
|
-
return false;
|
|
184
|
-
}
|
|
185
|
-
try {
|
|
186
|
-
authStore.loading.set(true);
|
|
187
|
-
authStore.error.set(null);
|
|
188
|
-
await authClient.signIn.email({ email, password }, {
|
|
189
|
-
onSuccess: (context) => {
|
|
190
|
-
const token = context.response.headers.get("set-auth-token");
|
|
191
|
-
if (token) {
|
|
192
|
-
tokenStorage.save(token);
|
|
193
|
-
}
|
|
194
|
-
},
|
|
195
|
-
onError: (context) => {
|
|
196
|
-
authStore.error.set(context.error.message || "Login failed");
|
|
197
|
-
},
|
|
198
|
-
});
|
|
199
|
-
authStore.loading.set(false);
|
|
200
|
-
return true;
|
|
201
|
-
}
|
|
202
|
-
catch (error) {
|
|
203
|
-
const message = error instanceof Error ? error.message : "Login failed";
|
|
204
|
-
authStore.error.set(message);
|
|
205
|
-
authStore.loading.set(false);
|
|
206
|
-
return false;
|
|
207
|
-
}
|
|
110
|
+
handleUnauthorized() {
|
|
111
|
+
this.clearAuth();
|
|
208
112
|
},
|
|
113
|
+
// ============================================================
|
|
114
|
+
// Active 状态更新
|
|
115
|
+
// ============================================================
|
|
209
116
|
/**
|
|
210
|
-
*
|
|
211
|
-
*
|
|
212
|
-
* @param email - 邮箱
|
|
213
|
-
* @param password - 密码
|
|
214
|
-
* @param name - 用户名
|
|
215
|
-
* @returns 是否注册成功
|
|
117
|
+
* 更新活跃组织 ID
|
|
216
118
|
*/
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
return false;
|
|
224
|
-
}
|
|
225
|
-
try {
|
|
226
|
-
authStore.loading.set(true);
|
|
227
|
-
authStore.error.set(null);
|
|
228
|
-
await authClient.signUp.email({ email, password, name }, {
|
|
229
|
-
onSuccess: (context) => {
|
|
230
|
-
const token = context.response.headers.get("set-auth-token");
|
|
231
|
-
if (token) {
|
|
232
|
-
tokenStorage.save(token);
|
|
233
|
-
}
|
|
234
|
-
},
|
|
235
|
-
onError: (context) => {
|
|
236
|
-
authStore.error.set(context.error.message || "Sign up failed");
|
|
237
|
-
},
|
|
119
|
+
setActiveOrganizationId(organizationId) {
|
|
120
|
+
const currentUser = authStore.user.get();
|
|
121
|
+
if (currentUser) {
|
|
122
|
+
authStore.user.set({
|
|
123
|
+
...currentUser,
|
|
124
|
+
activeOrganizationId: organizationId ?? undefined,
|
|
238
125
|
});
|
|
239
|
-
authStore.loading.set(false);
|
|
240
|
-
return true;
|
|
241
|
-
}
|
|
242
|
-
catch (error) {
|
|
243
|
-
const message = error instanceof Error ? error.message : "Sign up failed";
|
|
244
|
-
authStore.error.set(message);
|
|
245
|
-
authStore.loading.set(false);
|
|
246
|
-
return false;
|
|
247
126
|
}
|
|
248
127
|
},
|
|
249
128
|
/**
|
|
250
|
-
*
|
|
129
|
+
* 更新活跃团队 ID
|
|
251
130
|
*/
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
await authClient.signOut();
|
|
260
|
-
authStore.user.set(null);
|
|
261
|
-
authStore.isAuthenticated.set(false);
|
|
262
|
-
tokenStorage.clear();
|
|
263
|
-
if (redirectTo) {
|
|
264
|
-
window.location.href = redirectTo;
|
|
265
|
-
}
|
|
266
|
-
}
|
|
267
|
-
catch (error) {
|
|
268
|
-
const message = error instanceof Error ? error.message : "Sign out failed";
|
|
269
|
-
authStore.error.set(message);
|
|
270
|
-
authStore.user.set(null);
|
|
271
|
-
authStore.isAuthenticated.set(false);
|
|
272
|
-
tokenStorage.clear();
|
|
273
|
-
}
|
|
274
|
-
finally {
|
|
275
|
-
authStore.loading.set(false);
|
|
131
|
+
setActiveTeamId(teamId) {
|
|
132
|
+
const currentUser = authStore.user.get();
|
|
133
|
+
if (currentUser) {
|
|
134
|
+
authStore.user.set({
|
|
135
|
+
...currentUser,
|
|
136
|
+
activeTeamId: teamId ?? undefined,
|
|
137
|
+
});
|
|
276
138
|
}
|
|
277
139
|
},
|
|
140
|
+
// ============================================================
|
|
141
|
+
// 初始化
|
|
142
|
+
// ============================================================
|
|
278
143
|
/**
|
|
279
|
-
*
|
|
144
|
+
* 初始化认证状态
|
|
280
145
|
*/
|
|
281
|
-
|
|
146
|
+
initialize(user, isLoaded) {
|
|
282
147
|
if (user) {
|
|
283
|
-
|
|
284
|
-
authStore.isAuthenticated.set(true);
|
|
148
|
+
this.setAuthenticated(user);
|
|
285
149
|
}
|
|
286
150
|
else {
|
|
287
151
|
authStore.user.set(null);
|
|
288
152
|
authStore.isAuthenticated.set(false);
|
|
289
153
|
}
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
* 获取当前用户
|
|
293
|
-
*/
|
|
294
|
-
getUser() {
|
|
295
|
-
return authStore.user.get();
|
|
154
|
+
authStore.isLoaded.set(isLoaded);
|
|
155
|
+
authStore.loading.set(!isLoaded);
|
|
296
156
|
},
|
|
297
157
|
};
|
|
298
158
|
}
|
|
159
|
+
// ============================================================
|
|
160
|
+
// 兼容性导出(保持向后兼容)
|
|
161
|
+
// ============================================================
|
|
162
|
+
/**
|
|
163
|
+
* @deprecated 使用 createStoreActions 代替
|
|
164
|
+
* 保留此函数以保持向后兼容性
|
|
165
|
+
*/
|
|
166
|
+
export { createStoreActions as createAuthActions };
|
package/dist/store/computed.d.ts
CHANGED
|
@@ -1,3 +1,9 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 认证 Computed(派生状态)
|
|
3
|
+
*
|
|
4
|
+
* 基于 authStore 派生的响应式状态
|
|
5
|
+
* 这些都是只读的响应式值,会自动跟踪依赖并更新
|
|
6
|
+
*/
|
|
1
7
|
import type { Observable } from "@legendapp/state";
|
|
2
8
|
import type { AuthState } from "../types";
|
|
3
9
|
/**
|
|
@@ -5,8 +11,73 @@ import type { AuthState } from "../types";
|
|
|
5
11
|
*/
|
|
6
12
|
export declare function createAuthComputed(authStore: Observable<AuthState>): {
|
|
7
13
|
/**
|
|
8
|
-
*
|
|
14
|
+
* 是否正在初始化(未加载完成)
|
|
9
15
|
*/
|
|
10
16
|
isInitializing: import("@legendapp/state").ObservableBoolean;
|
|
17
|
+
/**
|
|
18
|
+
* 是否准备就绪(已加载且已认证)
|
|
19
|
+
*/
|
|
20
|
+
isReady: import("@legendapp/state").ObservableBoolean;
|
|
21
|
+
/**
|
|
22
|
+
* 是否未认证(已加载但未认证)
|
|
23
|
+
*/
|
|
24
|
+
isUnauthenticated: import("@legendapp/state").ObservableBoolean;
|
|
25
|
+
/**
|
|
26
|
+
* 是否有错误
|
|
27
|
+
*/
|
|
28
|
+
hasError: import("@legendapp/state").ObservableBoolean;
|
|
29
|
+
/**
|
|
30
|
+
* 当前用户 ID
|
|
31
|
+
*/
|
|
32
|
+
userId: import("@legendapp/state").ObservablePrimitive<string | null>;
|
|
33
|
+
/**
|
|
34
|
+
* 当前用户邮箱
|
|
35
|
+
*/
|
|
36
|
+
userEmail: import("@legendapp/state").ObservablePrimitive<string | null>;
|
|
37
|
+
/**
|
|
38
|
+
* 当前用户名称
|
|
39
|
+
*/
|
|
40
|
+
userName: import("@legendapp/state").ObservablePrimitive<string | null>;
|
|
41
|
+
/**
|
|
42
|
+
* 当前用户头像
|
|
43
|
+
*/
|
|
44
|
+
userImage: import("@legendapp/state").ObservablePrimitive<string | null>;
|
|
45
|
+
/**
|
|
46
|
+
* 邮箱是否已验证
|
|
47
|
+
*/
|
|
48
|
+
emailVerified: import("@legendapp/state").ObservableBoolean;
|
|
49
|
+
/**
|
|
50
|
+
* 当前活跃组织 ID
|
|
51
|
+
*/
|
|
52
|
+
activeOrganizationId: import("@legendapp/state").ObservablePrimitive<string | null>;
|
|
53
|
+
/**
|
|
54
|
+
* 当前活跃团队 ID
|
|
55
|
+
*/
|
|
56
|
+
activeTeamId: import("@legendapp/state").ObservablePrimitive<string | null>;
|
|
57
|
+
/**
|
|
58
|
+
* 伴生组织 ID(用户自己的组织)
|
|
59
|
+
*/
|
|
60
|
+
inherentOrganizationId: import("@legendapp/state").ObservablePrimitive<string | null>;
|
|
61
|
+
/**
|
|
62
|
+
* 伴生团队 ID(用户自己的团队)
|
|
63
|
+
*/
|
|
64
|
+
inherentTeamId: import("@legendapp/state").ObservablePrimitive<string | null>;
|
|
65
|
+
/**
|
|
66
|
+
* 是否有活跃组织
|
|
67
|
+
*/
|
|
68
|
+
hasActiveOrganization: import("@legendapp/state").ObservableBoolean;
|
|
69
|
+
/**
|
|
70
|
+
* 是否有活跃团队
|
|
71
|
+
*/
|
|
72
|
+
hasActiveTeam: import("@legendapp/state").ObservableBoolean;
|
|
73
|
+
/**
|
|
74
|
+
* 是否在伴生组织中(当前活跃组织是否是伴生组织)
|
|
75
|
+
*/
|
|
76
|
+
isInInherentOrganization: import("@legendapp/state").ObservableBoolean;
|
|
77
|
+
/**
|
|
78
|
+
* 是否在伴生团队中(当前活跃团队是否是伴生团队)
|
|
79
|
+
*/
|
|
80
|
+
isInInherentTeam: import("@legendapp/state").ObservableBoolean;
|
|
11
81
|
};
|
|
82
|
+
export type AuthComputed = ReturnType<typeof createAuthComputed>;
|
|
12
83
|
//# sourceMappingURL=computed.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"computed.d.ts","sourceRoot":"","sources":["../../src/store/computed.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"computed.d.ts","sourceRoot":"","sources":["../../src/store/computed.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAGH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAA;AAClD,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,UAAU,CAAA;AAEzC;;GAEG;AACH,wBAAgB,kBAAkB,CAAC,SAAS,EAAE,UAAU,CAAC,SAAS,CAAC;IAM/D;;OAEG;;IAGH;;OAEG;;IAGH;;OAEG;;IAGH;;OAEG;;IAOH;;OAEG;;IAGH;;OAEG;;IAGH;;OAEG;;IAGH;;OAEG;;IAGH;;OAEG;;IAOH;;OAEG;;IAGH;;OAEG;;IAGH;;OAEG;;IAGH;;OAEG;;IAGH;;OAEG;;IAGH;;OAEG;;IAGH;;OAEG;;IAOH;;OAEG;;EAON;AAED,MAAM,MAAM,YAAY,GAAG,UAAU,CAAC,OAAO,kBAAkB,CAAC,CAAA"}
|