@oxyhq/services 5.11.10 → 5.11.12
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/lib/commonjs/ui/components/AnimationExample.js +1 -1
- package/lib/commonjs/ui/components/AnimationExample.js.map +1 -1
- package/lib/commonjs/ui/components/FollowButton.js +1 -1
- package/lib/commonjs/ui/components/FollowButton.js.map +1 -1
- package/lib/commonjs/ui/components/Header.js +2 -2
- package/lib/commonjs/ui/components/Header.js.map +1 -1
- package/lib/commonjs/ui/components/OxyProvider.js +3 -3
- package/lib/commonjs/ui/components/OxyProvider.js.map +1 -1
- package/lib/commonjs/ui/components/StepBasedScreen.README.md +337 -0
- package/lib/commonjs/ui/components/StepBasedScreen.js +361 -0
- package/lib/commonjs/ui/components/StepBasedScreen.js.map +1 -0
- package/lib/commonjs/ui/components/icon/OxyIcon.js +3 -3
- package/lib/commonjs/ui/components/icon/OxyIcon.js.map +1 -1
- package/lib/commonjs/ui/components/internal/PinInput.js +1 -1
- package/lib/commonjs/ui/components/internal/PinInput.js.map +1 -1
- package/lib/commonjs/ui/components/photogrid/JustifiedPhotoGrid.js.map +1 -1
- package/lib/commonjs/ui/context/OxyContext.js +7 -7
- package/lib/commonjs/ui/context/OxyContext.js.map +1 -1
- package/lib/commonjs/ui/screens/PaymentGatewayScreen.js +1 -1
- package/lib/commonjs/ui/screens/PaymentGatewayScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/ProfileScreen.js +55 -55
- package/lib/commonjs/ui/screens/ProfileScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/RecoverAccountScreen.js +87 -219
- package/lib/commonjs/ui/screens/RecoverAccountScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/SignInScreen.js +138 -235
- package/lib/commonjs/ui/screens/SignInScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/SignUpScreen.js +139 -742
- package/lib/commonjs/ui/screens/SignUpScreen.js.map +1 -1
- package/lib/commonjs/ui/screens/internal/SignInPasswordStep.js +3 -3
- package/lib/commonjs/ui/screens/internal/SignInPasswordStep.js.map +1 -1
- package/lib/commonjs/ui/screens/internal/SignInUsernameStep.js +2 -2
- package/lib/commonjs/ui/screens/internal/SignInUsernameStep.js.map +1 -1
- package/lib/commonjs/ui/screens/steps/RecoverRequestStep.js +110 -0
- package/lib/commonjs/ui/screens/steps/RecoverRequestStep.js.map +1 -0
- package/lib/commonjs/ui/screens/steps/RecoverSuccessStep.js +138 -0
- package/lib/commonjs/ui/screens/steps/RecoverSuccessStep.js.map +1 -0
- package/lib/commonjs/ui/screens/steps/RecoverVerifyStep.js +141 -0
- package/lib/commonjs/ui/screens/steps/RecoverVerifyStep.js.map +1 -0
- package/lib/commonjs/ui/screens/steps/SignInPasswordStep.js +165 -0
- package/lib/commonjs/ui/screens/steps/SignInPasswordStep.js.map +1 -0
- package/lib/commonjs/ui/screens/steps/SignInUsernameStep.js +150 -0
- package/lib/commonjs/ui/screens/steps/SignInUsernameStep.js.map +1 -0
- package/lib/commonjs/ui/screens/steps/SignUpIdentityStep.js +171 -0
- package/lib/commonjs/ui/screens/steps/SignUpIdentityStep.js.map +1 -0
- package/lib/commonjs/ui/screens/steps/SignUpSecurityStep.js +163 -0
- package/lib/commonjs/ui/screens/steps/SignUpSecurityStep.js.map +1 -0
- package/lib/commonjs/ui/screens/steps/SignUpSummaryStep.js +170 -0
- package/lib/commonjs/ui/screens/steps/SignUpSummaryStep.js.map +1 -0
- package/lib/commonjs/ui/screens/steps/SignUpWelcomeStep.js +72 -0
- package/lib/commonjs/ui/screens/steps/SignUpWelcomeStep.js.map +1 -0
- package/lib/module/ui/components/AnimationExample.js +1 -1
- package/lib/module/ui/components/AnimationExample.js.map +1 -1
- package/lib/module/ui/components/FollowButton.js +1 -1
- package/lib/module/ui/components/FollowButton.js.map +1 -1
- package/lib/module/ui/components/Header.js +2 -2
- package/lib/module/ui/components/Header.js.map +1 -1
- package/lib/module/ui/components/OxyProvider.js +3 -3
- package/lib/module/ui/components/OxyProvider.js.map +1 -1
- package/lib/module/ui/components/Section.js.map +1 -1
- package/lib/module/ui/components/SectionTitle.js.map +1 -1
- package/lib/module/ui/components/StepBasedScreen.README.md +337 -0
- package/lib/module/ui/components/StepBasedScreen.js +356 -0
- package/lib/module/ui/components/StepBasedScreen.js.map +1 -0
- package/lib/module/ui/components/icon/FAIRWalletIcon.js.map +1 -1
- package/lib/module/ui/components/icon/OxyIcon.js +3 -3
- package/lib/module/ui/components/icon/OxyIcon.js.map +1 -1
- package/lib/module/ui/components/internal/PinInput.js +1 -1
- package/lib/module/ui/components/internal/PinInput.js.map +1 -1
- package/lib/module/ui/components/photogrid/JustifiedPhotoGrid.js.map +1 -1
- package/lib/module/ui/context/OxyContext.js +7 -7
- package/lib/module/ui/context/OxyContext.js.map +1 -1
- package/lib/module/ui/screens/PaymentGatewayScreen.js +1 -1
- package/lib/module/ui/screens/PaymentGatewayScreen.js.map +1 -1
- package/lib/module/ui/screens/ProfileScreen.js +55 -55
- package/lib/module/ui/screens/ProfileScreen.js.map +1 -1
- package/lib/module/ui/screens/RecoverAccountScreen.js +91 -222
- package/lib/module/ui/screens/RecoverAccountScreen.js.map +1 -1
- package/lib/module/ui/screens/SignInScreen.js +140 -237
- package/lib/module/ui/screens/SignInScreen.js.map +1 -1
- package/lib/module/ui/screens/SignUpScreen.js +141 -743
- package/lib/module/ui/screens/SignUpScreen.js.map +1 -1
- package/lib/module/ui/screens/internal/SignInPasswordStep.js +3 -3
- package/lib/module/ui/screens/internal/SignInPasswordStep.js.map +1 -1
- package/lib/module/ui/screens/internal/SignInUsernameStep.js +2 -2
- package/lib/module/ui/screens/internal/SignInUsernameStep.js.map +1 -1
- package/lib/module/ui/screens/steps/RecoverRequestStep.js +105 -0
- package/lib/module/ui/screens/steps/RecoverRequestStep.js.map +1 -0
- package/lib/module/ui/screens/steps/RecoverSuccessStep.js +133 -0
- package/lib/module/ui/screens/steps/RecoverSuccessStep.js.map +1 -0
- package/lib/module/ui/screens/steps/RecoverVerifyStep.js +136 -0
- package/lib/module/ui/screens/steps/RecoverVerifyStep.js.map +1 -0
- package/lib/module/ui/screens/steps/SignInPasswordStep.js +160 -0
- package/lib/module/ui/screens/steps/SignInPasswordStep.js.map +1 -0
- package/lib/module/ui/screens/steps/SignInUsernameStep.js +145 -0
- package/lib/module/ui/screens/steps/SignInUsernameStep.js.map +1 -0
- package/lib/module/ui/screens/steps/SignUpIdentityStep.js +166 -0
- package/lib/module/ui/screens/steps/SignUpIdentityStep.js.map +1 -0
- package/lib/module/ui/screens/steps/SignUpSecurityStep.js +158 -0
- package/lib/module/ui/screens/steps/SignUpSecurityStep.js.map +1 -0
- package/lib/module/ui/screens/steps/SignUpSummaryStep.js +165 -0
- package/lib/module/ui/screens/steps/SignUpSummaryStep.js.map +1 -0
- package/lib/module/ui/screens/steps/SignUpWelcomeStep.js +67 -0
- package/lib/module/ui/screens/steps/SignUpWelcomeStep.js.map +1 -0
- package/lib/typescript/models/interfaces.d.ts +4 -3
- package/lib/typescript/models/interfaces.d.ts.map +1 -1
- package/lib/typescript/ui/components/AnimationExample.d.ts +1 -1
- package/lib/typescript/ui/components/AnimationExample.d.ts.map +1 -1
- package/lib/typescript/ui/components/OxyPayButton.d.ts +2 -2
- package/lib/typescript/ui/components/OxyPayButton.d.ts.map +1 -1
- package/lib/typescript/ui/components/Section.d.ts +2 -1
- package/lib/typescript/ui/components/Section.d.ts.map +1 -1
- package/lib/typescript/ui/components/SectionTitle.d.ts +2 -1
- package/lib/typescript/ui/components/SectionTitle.d.ts.map +1 -1
- package/lib/typescript/ui/components/StepBasedScreen.d.ts +24 -0
- package/lib/typescript/ui/components/StepBasedScreen.d.ts.map +1 -0
- package/lib/typescript/ui/components/icon/FAIRWalletIcon.d.ts +2 -1
- package/lib/typescript/ui/components/icon/FAIRWalletIcon.d.ts.map +1 -1
- package/lib/typescript/ui/components/icon/OxyIcon.d.ts +1 -1
- package/lib/typescript/ui/components/icon/OxyIcon.d.ts.map +1 -1
- package/lib/typescript/ui/components/internal/PinInput.d.ts +9 -1
- package/lib/typescript/ui/components/internal/PinInput.d.ts.map +1 -1
- package/lib/typescript/ui/context/OxyContext.d.ts +2 -1
- package/lib/typescript/ui/context/OxyContext.d.ts.map +1 -1
- package/lib/typescript/ui/screens/PaymentGatewayScreen.d.ts +2 -2
- package/lib/typescript/ui/screens/PaymentGatewayScreen.d.ts.map +1 -1
- package/lib/typescript/ui/screens/ProfileScreen.d.ts.map +1 -1
- package/lib/typescript/ui/screens/RecoverAccountScreen.d.ts +2 -9
- package/lib/typescript/ui/screens/RecoverAccountScreen.d.ts.map +1 -1
- package/lib/typescript/ui/screens/SignInScreen.d.ts.map +1 -1
- package/lib/typescript/ui/screens/SignUpScreen.d.ts +1 -1
- package/lib/typescript/ui/screens/SignUpScreen.d.ts.map +1 -1
- package/lib/typescript/ui/screens/steps/RecoverRequestStep.d.ts +21 -0
- package/lib/typescript/ui/screens/steps/RecoverRequestStep.d.ts.map +1 -0
- package/lib/typescript/ui/screens/steps/RecoverSuccessStep.d.ts +18 -0
- package/lib/typescript/ui/screens/steps/RecoverSuccessStep.d.ts.map +1 -0
- package/lib/typescript/ui/screens/steps/RecoverVerifyStep.d.ts +24 -0
- package/lib/typescript/ui/screens/steps/RecoverVerifyStep.d.ts.map +1 -0
- package/lib/typescript/ui/screens/steps/SignInPasswordStep.d.ts +27 -0
- package/lib/typescript/ui/screens/steps/SignInPasswordStep.d.ts.map +1 -0
- package/lib/typescript/ui/screens/steps/SignInUsernameStep.d.ts +27 -0
- package/lib/typescript/ui/screens/steps/SignInUsernameStep.d.ts.map +1 -0
- package/lib/typescript/ui/screens/steps/SignUpIdentityStep.d.ts +25 -0
- package/lib/typescript/ui/screens/steps/SignUpIdentityStep.d.ts.map +1 -0
- package/lib/typescript/ui/screens/steps/SignUpSecurityStep.d.ts +26 -0
- package/lib/typescript/ui/screens/steps/SignUpSecurityStep.d.ts.map +1 -0
- package/lib/typescript/ui/screens/steps/SignUpSummaryStep.d.ts +16 -0
- package/lib/typescript/ui/screens/steps/SignUpSummaryStep.d.ts.map +1 -0
- package/lib/typescript/ui/screens/steps/SignUpWelcomeStep.d.ts +13 -0
- package/lib/typescript/ui/screens/steps/SignUpWelcomeStep.d.ts.map +1 -0
- package/package.json +2 -3
- package/src/models/interfaces.ts +5 -3
- package/src/ui/components/AnimationExample.tsx +9 -8
- package/src/ui/components/FollowButton.tsx +2 -2
- package/src/ui/components/Header.tsx +2 -2
- package/src/ui/components/OxyPayButton.tsx +2 -2
- package/src/ui/components/OxyProvider.tsx +4 -4
- package/src/ui/components/Section.tsx +7 -7
- package/src/ui/components/SectionTitle.tsx +2 -2
- package/src/ui/components/StepBasedScreen.README.md +337 -0
- package/src/ui/components/StepBasedScreen.tsx +417 -0
- package/src/ui/components/icon/FAIRWalletIcon.tsx +2 -2
- package/src/ui/components/icon/OxyIcon.tsx +10 -11
- package/src/ui/components/internal/PinInput.tsx +13 -4
- package/src/ui/components/photogrid/JustifiedPhotoGrid.tsx +1 -1
- package/src/ui/context/OxyContext.tsx +12 -11
- package/src/ui/screens/PaymentGatewayScreen.tsx +3 -3
- package/src/ui/screens/ProfileScreen.tsx +54 -54
- package/src/ui/screens/RecoverAccountScreen.tsx +98 -211
- package/src/ui/screens/SignInScreen.tsx +148 -271
- package/src/ui/screens/SignUpScreen.tsx +146 -748
- package/src/ui/screens/internal/SignInPasswordStep.tsx +3 -3
- package/src/ui/screens/internal/SignInUsernameStep.tsx +2 -2
- package/src/ui/screens/steps/RecoverRequestStep.tsx +130 -0
- package/src/ui/screens/steps/RecoverSuccessStep.tsx +131 -0
- package/src/ui/screens/steps/RecoverVerifyStep.tsx +153 -0
- package/src/ui/screens/steps/SignInPasswordStep.tsx +172 -0
- package/src/ui/screens/steps/SignInUsernameStep.tsx +176 -0
- package/src/ui/screens/steps/SignUpIdentityStep.tsx +204 -0
- package/src/ui/screens/steps/SignUpSecurityStep.tsx +191 -0
- package/src/ui/screens/steps/SignUpSummaryStep.tsx +130 -0
- package/src/ui/screens/steps/SignUpWelcomeStep.tsx +65 -0
|
@@ -1,42 +1,12 @@
|
|
|
1
1
|
import type React from 'react';
|
|
2
2
|
import { useState, useRef, useEffect, useMemo, useCallback } from 'react';
|
|
3
|
-
import {
|
|
4
|
-
View,
|
|
5
|
-
Text,
|
|
6
|
-
TextInput,
|
|
7
|
-
TouchableOpacity,
|
|
8
|
-
StyleSheet,
|
|
9
|
-
ActivityIndicator,
|
|
10
|
-
Platform,
|
|
11
|
-
KeyboardAvoidingView,
|
|
12
|
-
ScrollView,
|
|
13
|
-
TextStyle,
|
|
14
|
-
Dimensions,
|
|
15
|
-
StatusBar,
|
|
16
|
-
Alert,
|
|
17
|
-
} from 'react-native';
|
|
18
|
-
import Animated, {
|
|
19
|
-
useSharedValue,
|
|
20
|
-
useAnimatedStyle,
|
|
21
|
-
withSpring,
|
|
22
|
-
withTiming,
|
|
23
|
-
interpolate,
|
|
24
|
-
runOnJS,
|
|
25
|
-
Easing,
|
|
26
|
-
} from 'react-native-reanimated';
|
|
27
3
|
import type { BaseScreenProps } from '../navigation/types';
|
|
28
4
|
import { useOxy } from '../context/OxyContext';
|
|
29
|
-
import {
|
|
30
|
-
import OxyLogo from '../components/OxyLogo';
|
|
31
|
-
import Avatar from '../components/Avatar';
|
|
32
|
-
import { Ionicons } from '@expo/vector-icons';
|
|
33
|
-
import HighFive from '../../assets/illustrations/HighFive';
|
|
5
|
+
import { useThemeColors } from '../styles';
|
|
34
6
|
import { toast } from '../../lib/sonner';
|
|
35
|
-
import
|
|
36
|
-
import
|
|
37
|
-
import
|
|
38
|
-
import SignInUsernameStep from './internal/SignInUsernameStep';
|
|
39
|
-
import SignInPasswordStep from './internal/SignInPasswordStep';
|
|
7
|
+
import StepBasedScreen, { type StepConfig } from '../components/StepBasedScreen';
|
|
8
|
+
import SignInUsernameStep from './steps/SignInUsernameStep';
|
|
9
|
+
import SignInPasswordStep from './steps/SignInPasswordStep';
|
|
40
10
|
|
|
41
11
|
const SignInScreen: React.FC<BaseScreenProps> = ({
|
|
42
12
|
navigate,
|
|
@@ -47,39 +17,35 @@ const SignInScreen: React.FC<BaseScreenProps> = ({
|
|
|
47
17
|
username: initialUsername,
|
|
48
18
|
userProfile: initialUserProfile,
|
|
49
19
|
}) => {
|
|
50
|
-
// Only log props in development mode to reduce console noise
|
|
51
|
-
if (__DEV__) {
|
|
52
|
-
console.log('SignInScreen props:', { initialStep, initialUsername, initialUserProfile });
|
|
53
|
-
}
|
|
54
20
|
// Form data states
|
|
55
21
|
const [username, setUsername] = useState(initialUsername || '');
|
|
56
22
|
const [password, setPassword] = useState('');
|
|
57
23
|
const [errorMessage, setErrorMessage] = useState('');
|
|
58
24
|
const [userProfile, setUserProfile] = useState<any>(initialUserProfile || null);
|
|
59
25
|
const [showPassword, setShowPassword] = useState(false);
|
|
60
|
-
|
|
61
|
-
// Multi-step form states
|
|
62
|
-
const [currentStep, setCurrentStep] = useState(initialStep || 0);
|
|
63
26
|
const [isInputFocused, setIsInputFocused] = useState(false);
|
|
64
27
|
const [isValidating, setIsValidating] = useState(false);
|
|
65
28
|
const [validationStatus, setValidationStatus] = useState<'idle' | 'validating' | 'valid' | 'invalid'>(
|
|
66
29
|
initialUserProfile ? 'valid' : 'idle'
|
|
67
30
|
);
|
|
68
31
|
|
|
69
|
-
//
|
|
70
|
-
|
|
32
|
+
// Monitor username state changes
|
|
33
|
+
useEffect(() => {
|
|
34
|
+
console.log('👀 SignInScreen username state changed:', username);
|
|
35
|
+
}, [username]);
|
|
71
36
|
|
|
72
|
-
//
|
|
73
|
-
const
|
|
74
|
-
const slideAnim = useSharedValue(0);
|
|
75
|
-
const scaleAnim = useSharedValue(1);
|
|
76
|
-
const logoAnim = useSharedValue(0);
|
|
77
|
-
const progressAnim = useSharedValue(initialStep ? 1.0 : 0.5);
|
|
37
|
+
// Cache for validation results to prevent repeated API calls
|
|
38
|
+
const validationCache = useRef<Map<string, { profile: any }>>(new Map());
|
|
78
39
|
|
|
79
40
|
const { login, isLoading, user, isAuthenticated, sessions, oxyServices } = useOxy();
|
|
80
41
|
|
|
42
|
+
// Only log props in development mode to reduce console noise
|
|
43
|
+
if (__DEV__) {
|
|
44
|
+
console.log('SignInScreen props:', { initialStep, initialUsername, initialUserProfile });
|
|
45
|
+
console.log('🔧 oxyServices available:', !!oxyServices);
|
|
46
|
+
console.log('🔧 getProfileByUsername available:', typeof oxyServices?.getProfileByUsername);
|
|
47
|
+
}
|
|
81
48
|
const colors = useThemeColors(theme);
|
|
82
|
-
const commonStyles = createCommonStyles(theme);
|
|
83
49
|
|
|
84
50
|
// Check if this should be treated as "Add Account" mode
|
|
85
51
|
const isAddAccountMode = useMemo(() =>
|
|
@@ -87,66 +53,45 @@ const SignInScreen: React.FC<BaseScreenProps> = ({
|
|
|
87
53
|
[isAuthenticated, sessions]
|
|
88
54
|
);
|
|
89
55
|
|
|
90
|
-
// Memoized styles to prevent rerenders
|
|
91
|
-
const styles = useMemo(() => createAuthStyles(colors, theme), [colors, theme]);
|
|
92
|
-
|
|
93
|
-
// Initialize logo animation
|
|
94
|
-
useEffect(() => {
|
|
95
|
-
logoAnim.value = withSpring(1, {
|
|
96
|
-
damping: 15,
|
|
97
|
-
stiffness: 150,
|
|
98
|
-
});
|
|
99
|
-
}, [logoAnim]);
|
|
100
|
-
|
|
101
|
-
// Input focus handlers (no animation)
|
|
102
|
-
const handleInputFocus = useCallback(() => {
|
|
103
|
-
setIsInputFocused(true);
|
|
104
|
-
}, []);
|
|
105
|
-
|
|
106
|
-
const handleInputBlur = useCallback(() => {
|
|
107
|
-
setIsInputFocused(false);
|
|
108
|
-
}, []);
|
|
109
|
-
|
|
110
|
-
// Memoized input change handlers to prevent re-renders
|
|
111
|
-
const handleUsernameChange = useCallback((text: string) => {
|
|
112
|
-
setUsername(text);
|
|
113
|
-
// Clear error as soon as user edits username
|
|
114
|
-
if (errorMessage) setErrorMessage('');
|
|
115
|
-
setValidationStatus('idle');
|
|
116
|
-
}, [errorMessage]);
|
|
117
|
-
|
|
118
|
-
const handlePasswordChange = useCallback((text: string) => {
|
|
119
|
-
setPassword(text);
|
|
120
|
-
// Clear error as soon as user edits password
|
|
121
|
-
if (errorMessage) setErrorMessage('');
|
|
122
|
-
}, [errorMessage]);
|
|
123
|
-
|
|
124
56
|
// Username validation using core services with caching
|
|
125
57
|
const validateUsername = useCallback(async (usernameToValidate: string) => {
|
|
58
|
+
console.log('🔍 Validating username:', usernameToValidate);
|
|
59
|
+
|
|
126
60
|
if (!usernameToValidate || usernameToValidate.length < 3) {
|
|
61
|
+
console.log('❌ Username too short');
|
|
62
|
+
setValidationStatus('invalid');
|
|
63
|
+
setErrorMessage('Username must be at least 3 characters.');
|
|
64
|
+
return false;
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
// Safety check for oxyServices
|
|
68
|
+
if (!oxyServices || typeof oxyServices.getProfileByUsername !== 'function') {
|
|
69
|
+
console.error('🚨 oxyServices not available or getProfileByUsername not found');
|
|
127
70
|
setValidationStatus('invalid');
|
|
128
|
-
setErrorMessage('
|
|
71
|
+
setErrorMessage('Service unavailable. Please try again.');
|
|
129
72
|
return false;
|
|
130
73
|
}
|
|
131
74
|
|
|
132
|
-
// Check cache first
|
|
75
|
+
// Check cache first
|
|
133
76
|
const cached = validationCache.current.get(usernameToValidate);
|
|
134
|
-
|
|
135
|
-
|
|
77
|
+
if (cached) {
|
|
78
|
+
console.log('✅ Username found in cache:', cached.profile);
|
|
136
79
|
setUserProfile(cached.profile);
|
|
137
80
|
setValidationStatus('valid');
|
|
138
81
|
setErrorMessage('');
|
|
139
82
|
return true;
|
|
140
83
|
}
|
|
141
84
|
|
|
85
|
+
console.log('🔄 Validating username with API...');
|
|
142
86
|
setIsValidating(true);
|
|
143
87
|
setValidationStatus('validating');
|
|
144
88
|
|
|
145
89
|
try {
|
|
146
|
-
//
|
|
90
|
+
// Check if username exists
|
|
147
91
|
const profile = await oxyServices.getProfileByUsername(usernameToValidate);
|
|
92
|
+
console.log('📋 Profile response:', profile);
|
|
148
93
|
|
|
149
|
-
if (profile) {
|
|
94
|
+
if (profile && profile.username) {
|
|
150
95
|
const profileData = {
|
|
151
96
|
displayName: profile.name?.full || profile.name?.first || profile.username,
|
|
152
97
|
name: profile.username,
|
|
@@ -154,30 +99,42 @@ const SignInScreen: React.FC<BaseScreenProps> = ({
|
|
|
154
99
|
id: profile.id
|
|
155
100
|
};
|
|
156
101
|
|
|
102
|
+
console.log('✅ Username is valid:', profileData);
|
|
157
103
|
setUserProfile(profileData);
|
|
158
104
|
setValidationStatus('valid');
|
|
159
|
-
setErrorMessage('');
|
|
105
|
+
setErrorMessage('');
|
|
160
106
|
|
|
161
107
|
// Cache the result
|
|
162
108
|
validationCache.current.set(usernameToValidate, {
|
|
163
|
-
profile: profileData
|
|
164
|
-
timestamp: now
|
|
109
|
+
profile: profileData
|
|
165
110
|
});
|
|
166
111
|
|
|
167
112
|
return true;
|
|
168
113
|
} else {
|
|
114
|
+
console.log('❌ Username not found');
|
|
169
115
|
setValidationStatus('invalid');
|
|
170
116
|
setErrorMessage('Username not found.');
|
|
171
117
|
return false;
|
|
172
118
|
}
|
|
173
119
|
} catch (error: any) {
|
|
120
|
+
console.log('🚨 Validation error:', error);
|
|
121
|
+
|
|
174
122
|
// If user not found (404), username doesn't exist
|
|
175
123
|
if (error.status === 404 || error.code === 'USER_NOT_FOUND') {
|
|
124
|
+
console.log('❌ Username not found (404)');
|
|
176
125
|
setValidationStatus('invalid');
|
|
177
126
|
setErrorMessage('Username not found.');
|
|
178
127
|
return false;
|
|
179
128
|
}
|
|
180
129
|
|
|
130
|
+
// For development/testing: if API fails, allow any 3+ character username
|
|
131
|
+
if (__DEV__) {
|
|
132
|
+
console.log('⚠️ Development mode: allowing username due to API error');
|
|
133
|
+
setValidationStatus('valid');
|
|
134
|
+
setErrorMessage('');
|
|
135
|
+
return true;
|
|
136
|
+
}
|
|
137
|
+
|
|
181
138
|
// For other errors, show generic message
|
|
182
139
|
console.error('Username validation error:', error);
|
|
183
140
|
setValidationStatus('invalid');
|
|
@@ -188,113 +145,39 @@ const SignInScreen: React.FC<BaseScreenProps> = ({
|
|
|
188
145
|
}
|
|
189
146
|
}, [oxyServices]);
|
|
190
147
|
|
|
191
|
-
//
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
}
|
|
199
|
-
// Only validate if we haven't already validated this exact username
|
|
200
|
-
if (validationStatus === 'valid' && userProfile?.name === username) {
|
|
201
|
-
return;
|
|
202
|
-
}
|
|
203
|
-
// Remove debounce, only validate on continue
|
|
204
|
-
}, [username, validationStatus, userProfile?.name]);
|
|
205
|
-
|
|
206
|
-
// Cleanup cache on unmount and limit cache size
|
|
207
|
-
useEffect(() => {
|
|
208
|
-
return () => {
|
|
209
|
-
// Clear cache on unmount
|
|
210
|
-
validationCache.current.clear();
|
|
211
|
-
};
|
|
212
|
-
}, []);
|
|
213
|
-
|
|
214
|
-
// Clean up old cache entries periodically (older than 10 minutes)
|
|
215
|
-
useEffect(() => {
|
|
216
|
-
const cleanupInterval = setInterval(() => {
|
|
217
|
-
const now = Date.now();
|
|
218
|
-
const maxAge = 10 * 60 * 1000; // 10 minutes
|
|
219
|
-
|
|
220
|
-
for (const [key, value] of validationCache.current.entries()) {
|
|
221
|
-
if (now - value.timestamp > maxAge) {
|
|
222
|
-
validationCache.current.delete(key);
|
|
223
|
-
}
|
|
224
|
-
}
|
|
148
|
+
// Input change handlers
|
|
149
|
+
const handleUsernameChange = useCallback((text: string) => {
|
|
150
|
+
console.log('🔄 SignInScreen handleUsernameChange called:', text);
|
|
151
|
+
setUsername(text);
|
|
152
|
+
if (errorMessage) setErrorMessage('');
|
|
153
|
+
setValidationStatus('idle');
|
|
154
|
+
}, [errorMessage]);
|
|
225
155
|
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
const toDelete = entries.slice(0, entries.length - 50);
|
|
231
|
-
toDelete.forEach(([key]) => validationCache.current.delete(key));
|
|
232
|
-
}
|
|
233
|
-
}, 5 * 60 * 1000); // Clean up every 5 minutes
|
|
156
|
+
const handlePasswordChange = useCallback((text: string) => {
|
|
157
|
+
setPassword(text);
|
|
158
|
+
if (errorMessage) setErrorMessage('');
|
|
159
|
+
}, [errorMessage]);
|
|
234
160
|
|
|
235
|
-
|
|
161
|
+
const handleInputFocus = useCallback(() => {
|
|
162
|
+
setIsInputFocused(true);
|
|
236
163
|
}, []);
|
|
237
164
|
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
scaleAnim.value = withTiming(0.95, { duration: 150 });
|
|
242
|
-
|
|
243
|
-
// Fade out and then animate in new content
|
|
244
|
-
fadeAnim.value = withTiming(0, { duration: 200 }, (finished) => {
|
|
245
|
-
if (finished) {
|
|
246
|
-
runOnJS(setCurrentStep)(nextStep);
|
|
247
|
-
|
|
248
|
-
// Reset animations
|
|
249
|
-
slideAnim.value = -50;
|
|
250
|
-
scaleAnim.value = 0.95;
|
|
251
|
-
|
|
252
|
-
// Animate in new content
|
|
253
|
-
fadeAnim.value = withTiming(1, { duration: 300 });
|
|
254
|
-
slideAnim.value = withSpring(0, {
|
|
255
|
-
damping: 15,
|
|
256
|
-
stiffness: 200,
|
|
257
|
-
});
|
|
258
|
-
scaleAnim.value = withSpring(1, {
|
|
259
|
-
damping: 15,
|
|
260
|
-
stiffness: 200,
|
|
261
|
-
});
|
|
262
|
-
}
|
|
263
|
-
});
|
|
264
|
-
}, [fadeAnim, slideAnim, scaleAnim]);
|
|
265
|
-
|
|
266
|
-
const nextStep = useCallback(() => {
|
|
267
|
-
if (currentStep < 1) {
|
|
268
|
-
// Animate progress bar
|
|
269
|
-
progressAnim.value = withTiming(1.0, { duration: 300 });
|
|
270
|
-
animateTransition(currentStep + 1);
|
|
271
|
-
}
|
|
272
|
-
}, [currentStep, progressAnim, animateTransition]);
|
|
273
|
-
|
|
274
|
-
const prevStep = useCallback(() => {
|
|
275
|
-
if (currentStep > 0) {
|
|
276
|
-
// Animate progress bar
|
|
277
|
-
progressAnim.value = withTiming(0.5, { duration: 300 });
|
|
278
|
-
animateTransition(currentStep - 1);
|
|
279
|
-
}
|
|
280
|
-
}, [currentStep, progressAnim, animateTransition]);
|
|
165
|
+
const handleInputBlur = useCallback(() => {
|
|
166
|
+
setIsInputFocused(false);
|
|
167
|
+
}, []);
|
|
281
168
|
|
|
282
|
-
//
|
|
283
|
-
const
|
|
169
|
+
// Step validation and handlers
|
|
170
|
+
const validateUsernameStep = useCallback(async () => {
|
|
284
171
|
if (!username) {
|
|
285
172
|
setErrorMessage('Please enter your username.');
|
|
286
|
-
return;
|
|
173
|
+
return false;
|
|
287
174
|
}
|
|
288
175
|
setErrorMessage('');
|
|
289
176
|
setIsValidating(true);
|
|
290
177
|
const valid = await validateUsername(username);
|
|
291
178
|
setIsValidating(false);
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
return;
|
|
295
|
-
}
|
|
296
|
-
nextStep();
|
|
297
|
-
}, [username, validateUsername, nextStep]);
|
|
179
|
+
return valid;
|
|
180
|
+
}, [username, validateUsername]);
|
|
298
181
|
|
|
299
182
|
const handleSignIn = useCallback(async () => {
|
|
300
183
|
if (!password) {
|
|
@@ -316,93 +199,87 @@ const SignInScreen: React.FC<BaseScreenProps> = ({
|
|
|
316
199
|
}
|
|
317
200
|
}, [username, password, login, onAuthenticated, userProfile]);
|
|
318
201
|
|
|
319
|
-
//
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
scaleAnim={scaleAnim}
|
|
326
|
-
colors={colors}
|
|
327
|
-
isAddAccountMode={isAddAccountMode}
|
|
328
|
-
user={user}
|
|
329
|
-
errorMessage={errorMessage}
|
|
330
|
-
isInputFocused={isInputFocused}
|
|
331
|
-
username={username}
|
|
332
|
-
validationStatus={validationStatus}
|
|
333
|
-
userProfile={userProfile}
|
|
334
|
-
isValidating={isValidating}
|
|
335
|
-
handleInputFocus={handleInputFocus}
|
|
336
|
-
handleInputBlur={handleInputBlur}
|
|
337
|
-
handleUsernameChange={handleUsernameChange}
|
|
338
|
-
handleUsernameContinue={handleUsernameContinue}
|
|
339
|
-
navigate={navigate}
|
|
340
|
-
/>
|
|
341
|
-
), [
|
|
342
|
-
fadeAnim, slideAnim, scaleAnim, colors, isAddAccountMode, user?.username,
|
|
343
|
-
errorMessage, isInputFocused, username, validationStatus,
|
|
344
|
-
userProfile, isValidating, handleInputFocus, handleInputBlur, handleUsernameChange,
|
|
345
|
-
handleUsernameContinue, navigate, styles
|
|
346
|
-
]);
|
|
202
|
+
// Simple cleanup on unmount - that's all we need for username validation
|
|
203
|
+
useEffect(() => {
|
|
204
|
+
return () => {
|
|
205
|
+
validationCache.current.clear();
|
|
206
|
+
};
|
|
207
|
+
}, []);
|
|
347
208
|
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
prevStep={prevStep}
|
|
369
|
-
navigate={navigate}
|
|
370
|
-
/>
|
|
371
|
-
), [
|
|
372
|
-
fadeAnim, slideAnim, scaleAnim, colors, userProfile, username, theme, logoAnim,
|
|
373
|
-
errorMessage, isInputFocused, password, showPassword,
|
|
374
|
-
handleInputFocus, handleInputBlur, handlePasswordChange, handleSignIn, isLoading, prevStep, styles, navigate
|
|
375
|
-
]);
|
|
209
|
+
// Step configurations
|
|
210
|
+
const steps: StepConfig[] = useMemo(() => [
|
|
211
|
+
{
|
|
212
|
+
id: 'username',
|
|
213
|
+
component: SignInUsernameStep,
|
|
214
|
+
canProceed: () => true, // Let the component handle validation internally
|
|
215
|
+
},
|
|
216
|
+
{
|
|
217
|
+
id: 'password',
|
|
218
|
+
component: SignInPasswordStep,
|
|
219
|
+
canProceed: () => true, // Let the component handle validation internally
|
|
220
|
+
},
|
|
221
|
+
], [username, password, validationStatus, validateUsername, handleSignIn]);
|
|
222
|
+
|
|
223
|
+
// Handle step completion (final step)
|
|
224
|
+
const handleComplete = useCallback(async (stepData: any[]) => {
|
|
225
|
+
// The sign-in is handled by the password step component
|
|
226
|
+
// This callback is here for interface compatibility
|
|
227
|
+
console.log('Sign-in flow completed');
|
|
228
|
+
}, []);
|
|
376
229
|
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
230
|
+
// Step data for the reusable component
|
|
231
|
+
const stepData = useMemo(() => [
|
|
232
|
+
{
|
|
233
|
+
username,
|
|
234
|
+
setUsername: handleUsernameChange,
|
|
235
|
+
errorMessage,
|
|
236
|
+
setErrorMessage,
|
|
237
|
+
validationStatus,
|
|
238
|
+
userProfile,
|
|
239
|
+
isValidating,
|
|
240
|
+
isInputFocused,
|
|
241
|
+
isAddAccountMode,
|
|
242
|
+
user,
|
|
243
|
+
handleInputFocus,
|
|
244
|
+
handleInputBlur,
|
|
245
|
+
validateUsername, // Add validation function
|
|
246
|
+
},
|
|
247
|
+
{
|
|
248
|
+
password,
|
|
249
|
+
setPassword: handlePasswordChange,
|
|
250
|
+
showPassword,
|
|
251
|
+
setShowPassword,
|
|
252
|
+
errorMessage,
|
|
253
|
+
setErrorMessage,
|
|
254
|
+
isLoading,
|
|
255
|
+
isInputFocused,
|
|
256
|
+
userProfile,
|
|
257
|
+
username,
|
|
258
|
+
handleInputFocus,
|
|
259
|
+
handleInputBlur,
|
|
260
|
+
handleSignIn, // Add sign-in function for password step
|
|
261
|
+
},
|
|
262
|
+
], [
|
|
263
|
+
username, password, errorMessage, validationStatus, userProfile,
|
|
264
|
+
isValidating, isInputFocused, isAddAccountMode, user, showPassword,
|
|
265
|
+
isLoading, handleUsernameChange, handlePasswordChange, handleInputFocus, handleInputBlur,
|
|
266
|
+
validateUsername, handleSignIn
|
|
267
|
+
]);
|
|
387
268
|
|
|
388
269
|
return (
|
|
389
|
-
<
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
>
|
|
403
|
-
{renderCurrentStep()}
|
|
404
|
-
</ScrollView>
|
|
405
|
-
</KeyboardAvoidingView>
|
|
270
|
+
<StepBasedScreen
|
|
271
|
+
steps={steps}
|
|
272
|
+
initialStep={initialStep}
|
|
273
|
+
stepData={stepData}
|
|
274
|
+
onComplete={handleComplete}
|
|
275
|
+
navigate={navigate}
|
|
276
|
+
goBack={goBack}
|
|
277
|
+
onAuthenticated={onAuthenticated}
|
|
278
|
+
theme={theme}
|
|
279
|
+
showProgressIndicator={true}
|
|
280
|
+
enableAnimations={true}
|
|
281
|
+
oxyServices={oxyServices}
|
|
282
|
+
/>
|
|
406
283
|
);
|
|
407
284
|
};
|
|
408
285
|
|