inflearn logo
강의

강의

N
챌린지

챌린지

멘토링

멘토링

N
클립

클립

로드맵

로드맵

지식공유

배달앱 클론코딩 [with React Native]

Redux, Config, EncryptedStorage, AsyncStorage의 차이

typescript 에러

1483

정이

작성한 질문수 8

0

errorResponse 에서 타입 에러가 납니다.

이것 저것 다 넣어봤는데 타입스크립트는 처음이라 뭘 고쳐야할 지 잘 모르겠어요ㅜㅜ

 

SignIn.tsx

import React, {useCallback, useRef, useState} from 'react';
import {
  ActivityIndicator,
  Alert,
  Pressable,
  StyleSheet,
  Text,
  TextInput,
  View,
} from 'react-native';
import {NativeStackScreenProps} from '@react-navigation/native-stack';
import {RootStackParamList} from '../../AppInner';
import DismissKeyboardView from '../components/DismissKeyboardView';
import { useAppDispatch } from '../store';
import axios, { AxiosError } from 'axios';
import Config from 'react-native-config';
import userSlice from '../slices/user';
import EncryptedStorage from 'react-native-encrypted-storage';

type SignInScreenProps = NativeStackScreenProps<RootStackParamList, 'SignIn'>;

function SignIn({navigation}: SignInScreenProps) {
  const dispatch = useAppDispatch();
  const [loading, setLoading] = useState(false);
  const [email, setEmail] = useState('');
  const [password, setPassword] = useState('');
  const emailRef = useRef<TextInput | null>(null);
  const passwordRef = useRef<TextInput | null>(null);

  const onChangeEmail = useCallback((text: string) => {
    setEmail(text.trim());
  }, []);
  const onChangePassword = useCallback((text: string) => {
    setPassword(text.trim());
  }, []);

  const onSubmit = useCallback(async() => {
    if (!email || !email.trim()) {
      return Alert.alert('알림', '이메일을 입력해주세요.');
    }
    if (!password || !password.trim()) {
      return Alert.alert('알림', '비밀번호를 입력해주세요.');
    }

    try {
      setLoading(true);
      const response = await axios.post(`${Config.API_URL}/login`, {
        email,
        password,
      });
      console.log(response.data);
      Alert.alert('알림', '로그인 되었습니다.');
      dispatch(
        userSlice.actions.setUser({
          name: response.data.data.name,
          email: response.data.data.email,
          accessToken: response.data.data.accessToken,
          refreshToken: response.data.data.refreshToken,
        }),
      );
      await EncryptedStorage.setItem(
        'refreshToken',
        response.data.data.refreshToken,
      );
    } catch (error) {
      const errorResponse = (error as AxiosError).response;
      if (errorResponse) {
        Alert.alert('알림', errorResponse.data.message);
      }
    } finally {
      setLoading(false);
    }
  }, [loading, dispatch, email, password]);

  const toSignUp = useCallback(() => {
    navigation.navigate('SignUp');
  }, [navigation]);

  const canGoNext = email && password;

  return (
    <DismissKeyboardView>
      <View style={styles.inputWrapper}>
        <Text style={styles.label}>이메일</Text>
        <TextInput
          style={styles.textInput}
          placeholder="이메일을 입력해주세요."
          placeholderTextColor="#666"
          value={email}
          onChangeText={onChangeEmail}
          importantForAccessibility="yes"
          autoComplete="email"
          textContentType="emailAddress" // IOS
          keyboardType="email-address"
          returnKeyType="next"
          clearButtonMode="while-editing"
          onSubmitEditing={() => {
            passwordRef.current?.focus();
          }}
          blurOnSubmit={false}
          ref={emailRef}
        />
      </View>
      <View style={styles.inputWrapper}>
        <Text style={styles.label}>비밀번호</Text>
        <TextInput
          style={styles.textInput}
          placeholder="비밀번호를 입력해주세요(영문,숫자,특수문자)"
          placeholderTextColor="#666"
          importantForAutofill="yes"
          value={password}
          onChangeText={onChangePassword}
          importantForAccessibility="yes"
          autoComplete="password"
          textContentType="password" // IOS
          // keyboardType="decimal-pad"
          secureTextEntry
          returnKeyType="send"
          clearButtonMode="while-editing" // IOS
          onSubmitEditing={onSubmit}
          ref={passwordRef}
        />
      </View>
      <View style={styles.buttonZone}>
        <Pressable
          onPress={onSubmit}
          style={
            !canGoNext
              ? styles.loginButton
              : StyleSheet.compose(styles.loginButton, styles.loginButtonActive)
          }
          disabled={!canGoNext || loading}>
          {loading ? (
            <ActivityIndicator color="white" />
          ) : (
            <Text style={styles.loginButtonText}>로그인</Text>
          )}
        </Pressable>
        <Pressable onPress={toSignUp}>
          <Text>회원가입하기</Text>
        </Pressable>
      </View>
    </DismissKeyboardView>
  );
}

const styles = StyleSheet.create({
  textInput: {
    padding: 5,
    borderBottomWidth: StyleSheet.hairlineWidth,
  },
  inputWrapper: {
    padding: 20,
  },
  label: {
    fontWeight: 'bold',
    fontSize: 16,
    marginBottom: 20,
  },
  buttonZone: {
    alignItems: 'center',
  },
  loginButton: {
    backgroundColor: 'gray',
    paddingHorizontal: 20,
    paddingVertical: 10,
    borderRadius: 5,
    marginBottom: 10,
  },
  loginButtonActive: {
    backgroundColor: 'blue',
  },
  loginButtonText: {
    color: 'white',
    fontSize: 16,
  },
});

export default SignIn;

react-native

답변 1

1

제로초(조현영)

제발 에러메시지도 같이 알려주세요...

0

정이

const errorResponse: AxiosResponse<unknown, any>

'errorResponse.data'은(는) 'unknown' 형식입니다.ts(18046)

1

제로초(조현영)

Alert.alert('알림', (errorResponse.data as { message: string }).message);

쉬운 방법은 이것이고요. 정석적인 방법은

if (axios.isAxiosError<{ message: string }>(error)) {
  Alert.alert('알림', error.response.data.message);
}
입니다.

앱실행시 네이버맵 [401] 에러

0

986

2

스타일링 라이브러리

0

147

2

expo, cli 선택 중에 고민이 있습니다.

0

167

2

JDK 버전이 달라도 괜찮나요?

0

223

2

dimenstion usewindowdeminstion

0

121

3

[맥 전용]환경 설정하기 1편 & [맥 전용]환경 설정하기 2편의 영상이 안나옵니다.

0

210

1

jdk11 버전과 gradle 버전의 호환성 관련 질문드립니다.

0

399

2

강의 외 질문입니다!

0

157

2

react native랑 맞는 ui 라이브러리 어떤게 좋을까요?

0

1498

2

react native와 spring boot 연결

0

355

1

java가 아닌 .kt에서 code push 에러가 발생합니다.

0

214

2

flipper 239 에러가 발생합니다.

0

165

2

package.json에 /lib/panino.js 문제입니다.

0

470

2

window - mac 협업 과정 질문합니다

0

215

1

ios 빌드 중 RCTBridgeDelegate.h import 오류

0

289

2

ios 앱 빌드 중 hermesEnabled 관련 오류발생

0

239

2

Socket 연결시 질문 드립니다.!

0

152

2

wifi 환경에서 axios 통신이 로컬서버에서 안됩니다.

0

426

2

iOS render error 질문드립니다.

0

410

2

iOS 가상머신 오류

0

165

2

npc react init 명령어 실행시 발생되는 오류

0

220

1

nom start 시 오류

0

116

1

NextJS 기반으로 만들어서 웹뷰 React Native로 배포 가능한가요?

0

1001

2

안드로이드 rn75 버전에 맞게 설정 중에 android13 다운로드에 대해서 막혔습니다!

0

184

2