@umituz/react-native-auth 3.6.72 → 3.6.74
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/package.json +1 -1
- package/src/domain/value-objects/AuthConfig.ts +9 -56
- package/src/index.ts +15 -111
- package/src/infrastructure/adapters/StorageProviderAdapter.ts +1 -4
- package/src/infrastructure/providers/FirebaseAuthProvider.ts +5 -32
- package/src/infrastructure/repositories/AuthRepository.ts +0 -5
- package/src/infrastructure/services/AnonymousModeService.ts +6 -20
- package/src/infrastructure/services/AuthEventService.ts +2 -4
- package/src/infrastructure/services/initializeAuth.ts +2 -11
- package/src/infrastructure/utils/AuthErrorMapper.ts +0 -4
- package/src/infrastructure/utils/authStateHandler.ts +2 -4
- package/src/infrastructure/utils/listener/anonymousSignInHandler.ts +2 -22
- package/src/infrastructure/utils/listener/listenerLifecycle.util.ts +144 -0
- package/src/infrastructure/utils/listener/listenerState.util.ts +125 -0
- package/src/init/createAuthInitModule.ts +3 -22
- package/src/presentation/components/AccountActions.tsx +11 -43
- package/src/presentation/components/AuthBottomSheet.tsx +1 -17
- package/src/presentation/components/ProfileSection.tsx +78 -108
- package/src/presentation/components/RegisterForm.tsx +6 -28
- package/src/presentation/hooks/useAccountManagement.ts +0 -7
- package/src/presentation/hooks/useAuth.ts +2 -4
- package/src/presentation/hooks/useAuthBottomSheet.ts +23 -79
- package/src/presentation/hooks/useGoogleAuth.ts +0 -3
- package/src/presentation/hooks/useLoginForm.ts +26 -30
- package/src/presentation/hooks/useProfileEdit.ts +56 -64
- package/src/presentation/hooks/useRegisterForm.ts +41 -44
- package/src/presentation/providers/AuthProvider.tsx +2 -7
- package/src/presentation/stores/authModalStore.ts +0 -7
- package/src/presentation/stores/authStore.ts +1 -28
- package/src/presentation/stores/initializeAuthListener.ts +30 -160
- package/src/presentation/utils/accountDeleteHandler.util.ts +0 -51
- package/src/presentation/utils/authTransition.util.ts +72 -0
- package/src/presentation/utils/form/formFieldState.util.ts +82 -0
- package/src/presentation/utils/form/formValidation.util.ts +173 -0
- package/src/presentation/utils/socialAuthHandler.util.ts +106 -0
|
@@ -0,0 +1,173 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Form Validation Utilities
|
|
3
|
+
* Shared validation logic for all auth forms
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import { useCallback } from "react";
|
|
7
|
+
import {
|
|
8
|
+
validateEmail,
|
|
9
|
+
validatePasswordForLogin,
|
|
10
|
+
validatePasswordForRegister,
|
|
11
|
+
validatePasswordConfirmation,
|
|
12
|
+
} from "../../../infrastructure/utils/AuthValidation";
|
|
13
|
+
import type { PasswordConfig } from "../../../domain/value-objects/AuthConfig";
|
|
14
|
+
|
|
15
|
+
export interface FormValidationError {
|
|
16
|
+
field: string;
|
|
17
|
+
message: string;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
export interface FormValidationResult {
|
|
21
|
+
isValid: boolean;
|
|
22
|
+
errors: FormValidationError[];
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
export interface LoginFormValues {
|
|
26
|
+
email: string;
|
|
27
|
+
password: string;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
export interface RegisterFormValues {
|
|
31
|
+
displayName?: string;
|
|
32
|
+
email: string;
|
|
33
|
+
password: string;
|
|
34
|
+
confirmPassword: string;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
export interface ProfileFormValues {
|
|
38
|
+
displayName: string;
|
|
39
|
+
email: string;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
/**
|
|
43
|
+
* Validate login form fields
|
|
44
|
+
* @param values - Form values to validate
|
|
45
|
+
* @param getErrorMessage - Function to get localized error messages
|
|
46
|
+
* @returns Validation result
|
|
47
|
+
*/
|
|
48
|
+
export function validateLoginForm(
|
|
49
|
+
values: LoginFormValues,
|
|
50
|
+
getErrorMessage: (key: string) => string
|
|
51
|
+
): FormValidationResult {
|
|
52
|
+
const errors: FormValidationError[] = [];
|
|
53
|
+
|
|
54
|
+
const emailResult = validateEmail(values.email.trim());
|
|
55
|
+
if (!emailResult.isValid && emailResult.error) {
|
|
56
|
+
errors.push({ field: "email", message: getErrorMessage(emailResult.error) });
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
const passwordResult = validatePasswordForLogin(values.password);
|
|
60
|
+
if (!passwordResult.isValid && passwordResult.error) {
|
|
61
|
+
errors.push({ field: "password", message: getErrorMessage(passwordResult.error) });
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
return {
|
|
65
|
+
isValid: errors.length === 0,
|
|
66
|
+
errors,
|
|
67
|
+
};
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
/**
|
|
71
|
+
* Validate register form fields
|
|
72
|
+
* @param values - Form values to validate
|
|
73
|
+
* @param getErrorMessage - Function to get localized error messages
|
|
74
|
+
* @param passwordConfig - Password configuration
|
|
75
|
+
* @returns Validation result
|
|
76
|
+
*/
|
|
77
|
+
export function validateRegisterForm(
|
|
78
|
+
values: RegisterFormValues,
|
|
79
|
+
getErrorMessage: (key: string) => string,
|
|
80
|
+
passwordConfig: PasswordConfig
|
|
81
|
+
): FormValidationResult {
|
|
82
|
+
const errors: FormValidationError[] = [];
|
|
83
|
+
|
|
84
|
+
const emailResult = validateEmail(values.email.trim());
|
|
85
|
+
if (!emailResult.isValid && emailResult.error) {
|
|
86
|
+
errors.push({ field: "email", message: getErrorMessage(emailResult.error) });
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
const passwordResult = validatePasswordForRegister(values.password, passwordConfig);
|
|
90
|
+
if (!passwordResult.isValid && passwordResult.error) {
|
|
91
|
+
errors.push({ field: "password", message: getErrorMessage(passwordResult.error) });
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
const confirmResult = validatePasswordConfirmation(values.password, values.confirmPassword);
|
|
95
|
+
if (!confirmResult.isValid && confirmResult.error) {
|
|
96
|
+
errors.push({ field: "confirmPassword", message: getErrorMessage(confirmResult.error) });
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
return {
|
|
100
|
+
isValid: errors.length === 0,
|
|
101
|
+
errors,
|
|
102
|
+
};
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
/**
|
|
106
|
+
* Validate profile form fields
|
|
107
|
+
* @param values - Form values to validate
|
|
108
|
+
* @returns Validation result
|
|
109
|
+
*/
|
|
110
|
+
export function validateProfileForm(values: ProfileFormValues): FormValidationResult {
|
|
111
|
+
const errors: FormValidationError[] = [];
|
|
112
|
+
|
|
113
|
+
if (!values.displayName.trim()) {
|
|
114
|
+
errors.push({ field: "displayName", message: "Display name is required" });
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
if (values.email) {
|
|
118
|
+
const emailResult = validateEmail(values.email);
|
|
119
|
+
if (!emailResult.isValid && emailResult.error) {
|
|
120
|
+
errors.push({ field: "email", message: emailResult.error });
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
return {
|
|
125
|
+
isValid: errors.length === 0,
|
|
126
|
+
errors,
|
|
127
|
+
};
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
/**
|
|
131
|
+
* Convert validation errors to field error object
|
|
132
|
+
* @param errors - Validation errors
|
|
133
|
+
* @returns Object mapping field names to error messages
|
|
134
|
+
*/
|
|
135
|
+
export function errorsToFieldErrors(
|
|
136
|
+
errors: FormValidationError[]
|
|
137
|
+
): Record<string, string> {
|
|
138
|
+
const result: Record<string, string> = {};
|
|
139
|
+
for (const error of errors) {
|
|
140
|
+
result[error.field] = error.message;
|
|
141
|
+
}
|
|
142
|
+
return result;
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
/**
|
|
146
|
+
* Hook for form validation with error message resolution
|
|
147
|
+
* @param getErrorMessage - Function to get localized error messages
|
|
148
|
+
* @returns Validation functions
|
|
149
|
+
*/
|
|
150
|
+
export function useFormValidation(getErrorMessage: (key: string) => string) {
|
|
151
|
+
const validateLogin = useCallback(
|
|
152
|
+
(values: LoginFormValues) => validateLoginForm(values, getErrorMessage),
|
|
153
|
+
[getErrorMessage]
|
|
154
|
+
);
|
|
155
|
+
|
|
156
|
+
const validateRegister = useCallback(
|
|
157
|
+
(values: RegisterFormValues, passwordConfig: PasswordConfig) =>
|
|
158
|
+
validateRegisterForm(values, getErrorMessage, passwordConfig),
|
|
159
|
+
[getErrorMessage]
|
|
160
|
+
);
|
|
161
|
+
|
|
162
|
+
const validateProfile = useCallback(
|
|
163
|
+
(values: ProfileFormValues) => validateProfileForm(values),
|
|
164
|
+
[]
|
|
165
|
+
);
|
|
166
|
+
|
|
167
|
+
return {
|
|
168
|
+
validateLogin,
|
|
169
|
+
validateRegister,
|
|
170
|
+
validateProfile,
|
|
171
|
+
errorsToFieldErrors,
|
|
172
|
+
};
|
|
173
|
+
}
|
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Social Auth Handler Utilities
|
|
3
|
+
* Manages social authentication state and handlers
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import { useState, useCallback } from "react";
|
|
7
|
+
import type { SocialAuthProvider } from "../../domain/value-objects/AuthConfig";
|
|
8
|
+
import { Platform } from "react-native";
|
|
9
|
+
|
|
10
|
+
export interface SocialAuthHandlers {
|
|
11
|
+
googleLoading: boolean;
|
|
12
|
+
appleLoading: boolean;
|
|
13
|
+
handleGoogleSignIn: () => Promise<void>;
|
|
14
|
+
handleAppleSignIn: () => Promise<void>;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
export interface SocialAuthConfig {
|
|
18
|
+
google?: { iosClientId?: string; webClientId?: string; androidClientId?: string };
|
|
19
|
+
apple?: { enabled: boolean };
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
/**
|
|
23
|
+
* Hook for managing social auth loading states
|
|
24
|
+
*/
|
|
25
|
+
export function useSocialAuthLoading() {
|
|
26
|
+
const [googleLoading, setGoogleLoading] = useState(false);
|
|
27
|
+
const [appleLoading, setAppleLoading] = useState(false);
|
|
28
|
+
|
|
29
|
+
const createGoogleHandler = useCallback(
|
|
30
|
+
(handler: () => Promise<void>) => {
|
|
31
|
+
return async () => {
|
|
32
|
+
setGoogleLoading(true);
|
|
33
|
+
try {
|
|
34
|
+
await handler();
|
|
35
|
+
} finally {
|
|
36
|
+
setGoogleLoading(false);
|
|
37
|
+
}
|
|
38
|
+
};
|
|
39
|
+
},
|
|
40
|
+
[]
|
|
41
|
+
);
|
|
42
|
+
|
|
43
|
+
const createAppleHandler = useCallback(
|
|
44
|
+
(handler: () => Promise<void>) => {
|
|
45
|
+
return async () => {
|
|
46
|
+
setAppleLoading(true);
|
|
47
|
+
try {
|
|
48
|
+
await handler();
|
|
49
|
+
} finally {
|
|
50
|
+
setAppleLoading(false);
|
|
51
|
+
}
|
|
52
|
+
};
|
|
53
|
+
},
|
|
54
|
+
[]
|
|
55
|
+
);
|
|
56
|
+
|
|
57
|
+
return {
|
|
58
|
+
googleLoading,
|
|
59
|
+
appleLoading,
|
|
60
|
+
setGoogleLoading,
|
|
61
|
+
setAppleLoading,
|
|
62
|
+
createGoogleHandler,
|
|
63
|
+
createAppleHandler,
|
|
64
|
+
};
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
/**
|
|
68
|
+
* Determine enabled social auth providers
|
|
69
|
+
*/
|
|
70
|
+
export function determineEnabledProviders(
|
|
71
|
+
config: SocialAuthConfig | undefined,
|
|
72
|
+
appleAvailable: boolean,
|
|
73
|
+
googleConfigured: boolean
|
|
74
|
+
): SocialAuthProvider[] {
|
|
75
|
+
const providers: SocialAuthProvider[] = [];
|
|
76
|
+
|
|
77
|
+
if (Platform.OS === "ios" && config?.apple?.enabled && appleAvailable) {
|
|
78
|
+
providers.push("apple");
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
if (googleConfigured) {
|
|
82
|
+
providers.push("google");
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
return providers;
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
/**
|
|
89
|
+
* Create social auth handlers
|
|
90
|
+
*/
|
|
91
|
+
export function createSocialAuthHandlers(
|
|
92
|
+
googleSignIn: (() => Promise<void>) | undefined,
|
|
93
|
+
appleSignIn: (() => Promise<void>) | undefined,
|
|
94
|
+
internalGoogleHandler: (() => Promise<void>) | undefined,
|
|
95
|
+
internalAppleHandler: (() => Promise<void>) | undefined
|
|
96
|
+
): SocialAuthHandlers {
|
|
97
|
+
const googleHandler = googleSignIn || internalGoogleHandler;
|
|
98
|
+
const appleHandler = appleSignIn || internalAppleHandler;
|
|
99
|
+
|
|
100
|
+
return {
|
|
101
|
+
googleLoading: false,
|
|
102
|
+
appleLoading: false,
|
|
103
|
+
handleGoogleSignIn: googleHandler || (async () => {}),
|
|
104
|
+
handleAppleSignIn: appleHandler || (async () => {}),
|
|
105
|
+
};
|
|
106
|
+
}
|