|
|
@@ -0,0 +1,245 @@
|
|
|
+import { View, Text, ScrollView, StyleSheet, Pressable } from 'react-native';
|
|
|
+import React, { useContext, useEffect, useState } from 'react';
|
|
|
+import { SafeAreaView } from 'react-native-safe-area-context';
|
|
|
+import { router } from 'expo-router';
|
|
|
+import { CrossLogoSvg } from '../global/SVG';
|
|
|
+import { AuthContext } from '../../context/AuthProvider';
|
|
|
+import NormalInput from '../global/normal_input';
|
|
|
+import NormalButton from '../global/normal_button';
|
|
|
+import * as SecureStore from 'expo-secure-store';
|
|
|
+import { authenticationService } from '../../service/authService';
|
|
|
+
|
|
|
+const changePasswordPageComponent = () => {
|
|
|
+ const { user, setUser } = useContext(AuthContext);
|
|
|
+ const [token, setToken] = useState<string | null>(null);
|
|
|
+ const [currentPassword, setCurrentPassword] = useState<string | null>(null);
|
|
|
+ const [newPassword, setNewPassword] = useState<string | null>(null);
|
|
|
+ const [newConfirmPassword, setNewConfirmPassword] = useState<string | null>(
|
|
|
+ null
|
|
|
+ );
|
|
|
+ const [isPasswordVerified, setIsPasswordVerified] =
|
|
|
+ useState<boolean>(false);
|
|
|
+ const [error, setError] = useState<string | null>(null);
|
|
|
+ const [isLoading, setIsLoading] = useState(false);
|
|
|
+ const [isLoading2, setIsLoading2] = useState(false);
|
|
|
+
|
|
|
+ useEffect(() => {
|
|
|
+ const getToken = async () => {
|
|
|
+ const storedToken = await SecureStore.getItemAsync('accessToken');
|
|
|
+ setToken(storedToken);
|
|
|
+ };
|
|
|
+ getToken();
|
|
|
+ }, []);
|
|
|
+
|
|
|
+ const handleVerifyPassword = async (currentPassword: string) => {
|
|
|
+ try {
|
|
|
+ setIsLoading(true);
|
|
|
+ if (!currentPassword) {
|
|
|
+ setError('請輸入密碼');
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ if (!user || !user.email) {
|
|
|
+ setError('無法驗證用戶,請重新登錄');
|
|
|
+ return;
|
|
|
+ }
|
|
|
+
|
|
|
+ const success = await authenticationService.login(
|
|
|
+ user.email,
|
|
|
+ currentPassword
|
|
|
+ );
|
|
|
+ if (success) {
|
|
|
+ setIsPasswordVerified(true);
|
|
|
+ setError('');
|
|
|
+ return true;
|
|
|
+ } else {
|
|
|
+ setError('密碼錯誤,請稍後再試');
|
|
|
+ }
|
|
|
+ } catch (error) {
|
|
|
+ console.error('Error verifying password:', error);
|
|
|
+ setError('密碼錯誤,請稍後再試');
|
|
|
+ return false;
|
|
|
+ } finally {
|
|
|
+ setIsLoading(false);
|
|
|
+ }
|
|
|
+ };
|
|
|
+
|
|
|
+ const handlePasswordChange = async () => {
|
|
|
+ try {
|
|
|
+ setIsLoading2(true);
|
|
|
+ if (newPassword !== newConfirmPassword) {
|
|
|
+ setError('新密碼不相符');
|
|
|
+ return;
|
|
|
+ }
|
|
|
+
|
|
|
+ if (!newConfirmPassword || !token) {
|
|
|
+ setError('請輸入新密碼');
|
|
|
+ return;
|
|
|
+ }
|
|
|
+
|
|
|
+ const success = await authenticationService.changePassword(
|
|
|
+ newConfirmPassword,
|
|
|
+ token
|
|
|
+ );
|
|
|
+
|
|
|
+ if (success) {
|
|
|
+ setError('');
|
|
|
+ console.log('change password success');
|
|
|
+ router.replace('accountMainPage');
|
|
|
+ } else {
|
|
|
+ setError('密碼更改失敗,請稍後再試');
|
|
|
+ }
|
|
|
+ } catch (error) {
|
|
|
+ console.error('Error changing password:', error);
|
|
|
+ setError('發生錯誤,請稍後再試');
|
|
|
+ } finally {
|
|
|
+ setIsLoading2(false);
|
|
|
+ }
|
|
|
+ };
|
|
|
+
|
|
|
+ return (
|
|
|
+ <SafeAreaView
|
|
|
+ className="flex-1 bg-white"
|
|
|
+ edges={['top', 'right', 'left']}
|
|
|
+ >
|
|
|
+ <ScrollView className="flex-1 mx-[5%]">
|
|
|
+ <View style={{ marginTop: 25 }}>
|
|
|
+ <Pressable
|
|
|
+ onPress={() => {
|
|
|
+ if (router.canGoBack()) {
|
|
|
+ router.back();
|
|
|
+ } else {
|
|
|
+ router.replace('/accountMainPage');
|
|
|
+ }
|
|
|
+ }}
|
|
|
+ >
|
|
|
+ <CrossLogoSvg />
|
|
|
+ </Pressable>
|
|
|
+ <Text style={{ fontSize: 45, marginVertical: 25 }}>
|
|
|
+ 更改密碼
|
|
|
+ </Text>
|
|
|
+ <Text className="text-xl ">請輸入您現時的帳戶密碼</Text>
|
|
|
+ <View className="py-2">
|
|
|
+ <NormalInput
|
|
|
+ placeholder="帳戶密碼"
|
|
|
+ onChangeText={(t) => setCurrentPassword(t)}
|
|
|
+ secureTextEntry={true}
|
|
|
+ editable={!isPasswordVerified}
|
|
|
+ />
|
|
|
+ </View>
|
|
|
+
|
|
|
+ <NormalButton
|
|
|
+ title={
|
|
|
+ <Text style={{ color: '#fff' }}>
|
|
|
+ {isLoading
|
|
|
+ ? '驗證中...'
|
|
|
+ : isPasswordVerified
|
|
|
+ ? '已驗證'
|
|
|
+ : '下一步'}
|
|
|
+ </Text>
|
|
|
+ }
|
|
|
+ onPress={() => {
|
|
|
+ if (currentPassword) {
|
|
|
+ handleVerifyPassword(currentPassword);
|
|
|
+ }
|
|
|
+ }}
|
|
|
+ disabled={isPasswordVerified}
|
|
|
+ extendedStyle={
|
|
|
+ isPasswordVerified == true
|
|
|
+ ? { backgroundColor: '#70787C' }
|
|
|
+ : {}
|
|
|
+ }
|
|
|
+ />
|
|
|
+ </View>
|
|
|
+
|
|
|
+ {isPasswordVerified && (
|
|
|
+ <View
|
|
|
+ style={[
|
|
|
+ styles.hiddenPasswordFields,
|
|
|
+ isPasswordVerified
|
|
|
+ ? styles.opacityFull
|
|
|
+ : styles.opacityZero
|
|
|
+ ]}
|
|
|
+ >
|
|
|
+ <NormalInput
|
|
|
+ placeholder="新密碼"
|
|
|
+ onChangeText={(t) => setNewPassword(t)}
|
|
|
+ secureTextEntry={true}
|
|
|
+ textContentType={'oneTimeCode'}
|
|
|
+ />
|
|
|
+ <NormalInput
|
|
|
+ placeholder="確認密碼"
|
|
|
+ onChangeText={(t) => setNewConfirmPassword(t)}
|
|
|
+ secureTextEntry={true}
|
|
|
+ textContentType={'oneTimeCode'}
|
|
|
+ />
|
|
|
+ <NormalButton
|
|
|
+ title={
|
|
|
+ <Text style={{ color: '#fff' }}>
|
|
|
+ {isLoading2 ? '驗證中...' : '確認'}
|
|
|
+ </Text>
|
|
|
+ }
|
|
|
+ onPress={handlePasswordChange}
|
|
|
+ />
|
|
|
+ </View>
|
|
|
+ )}
|
|
|
+
|
|
|
+ {error && <Text style={styles.errorMessage}>{error}</Text>}
|
|
|
+ </ScrollView>
|
|
|
+ </SafeAreaView>
|
|
|
+ );
|
|
|
+};
|
|
|
+
|
|
|
+const styles = StyleSheet.create({
|
|
|
+ container: {
|
|
|
+ flex: 1,
|
|
|
+ marginHorizontal: 20
|
|
|
+ },
|
|
|
+
|
|
|
+ titleText: {
|
|
|
+ fontSize: 24,
|
|
|
+ fontWeight: '300'
|
|
|
+ },
|
|
|
+ bottomContainer: {
|
|
|
+ flex: 3,
|
|
|
+ paddingBottom: 100
|
|
|
+ },
|
|
|
+ breakline: {
|
|
|
+ width: 24,
|
|
|
+ height: 1,
|
|
|
+ backgroundColor: '#000000',
|
|
|
+ marginVertical: 17
|
|
|
+ },
|
|
|
+ text: {
|
|
|
+ fontSize: 18,
|
|
|
+ paddingBottom: 10
|
|
|
+ },
|
|
|
+ hiddenPasswordFields: {
|
|
|
+ gap: 10,
|
|
|
+ paddingTop: 10
|
|
|
+ },
|
|
|
+ opacityZero: {
|
|
|
+ opacity: 0
|
|
|
+ },
|
|
|
+ opacityFull: {
|
|
|
+ opacity: 1
|
|
|
+ },
|
|
|
+ errorMessage: {
|
|
|
+ fontSize: 14,
|
|
|
+ color: '#ff0033',
|
|
|
+ fontWeight: '400',
|
|
|
+ marginLeft: 10,
|
|
|
+ marginTop: 10
|
|
|
+ },
|
|
|
+ footer: { color: '#02677D', fontSize: 16, paddingVertical: 10 }
|
|
|
+});
|
|
|
+
|
|
|
+export default changePasswordPageComponent;
|
|
|
+
|
|
|
+// <NormalButton
|
|
|
+// title={<Text className="text-white text-lg">確認</Text>}
|
|
|
+// onPress={() => {
|
|
|
+// // poSSIBLY ADD ERROR HANDLING AND LOADING
|
|
|
+// // authenticationService.changePassword(password, token);
|
|
|
+// router.replace('accountMainPage');
|
|
|
+// }}
|
|
|
+// />
|