如何找到我的代码中的错误setstate?

huangapple go评论59阅读模式
英文:

How can I find the bad setstate in my code?

问题

我的React Native代码似乎执行正常。但我一直在遇到一个错误的setstate代码错误。以下是错误信息:

警告: 在呈现不同组件(`Login`)时无法更新组件(`ForwardRef(BaseNavigationContainer)`)。要定位`Login`内的错误`setState()`调用,请按照堆栈跟踪中描述的步骤查找,链接在https://reactjs.org/link/setstate-in-render中描述
  >> 在 Login(由 SceneView 创建)

我成功追踪到了可能引发错误的代码行(至少我认为是这样):Login @ Login.js:16

可能是这部分代码:

export function Login({ navigation }) {
  if (auth.currentUser) {
    navigation.navigate("Root");
  } else {
    onAuthStateChanged(auth, (user) => {
      if (user) {
        navigation.navigate("Root");
      }
    });
  }

以下是整个组件,似乎包含有问题的setState部分。我无法弄清楚如何消除这个错误。尽管所有的代码似乎都正常工作...

export function Login({ navigation }) {
  if (auth.currentUser) {
    navigation.navigate("Root");
  } else {
    onAuthStateChanged(auth, (user) => {
      if (user) {
        navigation.navigate("Root");
      }
    });
  }

  let [errorMessage, setErrorMessage] = React.useState("");
  let [email, setEmail] = React.useState("");
  let [password, setPassword] = React.useState("");

  let login = () => {
    if (email !== "" && password !== "") {
      signInWithEmailAndPassword(auth, email, password)
        .then((userCredential) => {
          // Signed in
          navigation.navigate("Home", { user: userCredential.user });
          // ...
        })
        .catch((error) => {
          setErrorMessage(error.message);
        });
    }
  };

  return (
    <View style={AppStyles.loginContainer}>
      <KeyboardAvoidingView
        style={AppStyles.backgroundCover}
        behavior={Platform.OS === "ios" ? "padding" : null}
        keyboardVerticalOffset={60}
      >
        <View style={AppStyles.loginScreen}>
          <Text style={AppStyles.textHeader}>Login</Text>
          <Text style={AppStyles.errorText}>{errorMessage}</Text>
          <TextInput
            style={AppStyles.input}
            placeholder="Email"
            placeholderTextColor="#fff"
            value={email}
            onChangeText={setEmail}
          />
          <TextInput
            style={AppStyles.input}
            placeholder="Password"
            placeholderTextColor="#fff"
            secureTextEntry={true}
            passwordRules={{ required: true, minLength: 6 }}
            value={password}
            onChangeText={setPassword}
          />
          <View style={AppStyles.rowContainer}>
            <Text style={AppStyles.text}>Don't have an account? </Text>
            <TextButton
              size="20px"
              text="Sign Up"
              color="#fff"
              onPress={() => navigation.navigate("Signup")}
            />
          </View>
          <View style={AppStyles.rowContainer}>
            <Text style={AppStyles.text}>Forgot your password? </Text>
            <TextButton
              size="20px"
              text="Reset"
              color="#fff"
              onPress={() => navigation.navigate("ResetPassword")}
            />
          </View>
          <TextButton
            size="20px"
            text="Login"
            backgroundColor="#83C9F4"
            paddingVertical={6}
            paddingHorizontal={12}
            onPress={login}
          />
        </View>
      </KeyboardAvoidingView>
    </View>
  );
}
英文:

My react native code seems to execute appropriately. I still keep getting a bad setstate code error. Here is the error:

Warning: Cannot update a component (`ForwardRef(BaseNavigationContainer)`) while rendering a different component (`Login`). To locate the bad setState() call inside `Login`, follow the stack trace as described in https://reactjs.org/link/setstate-in-render
  &gt;&gt; in Login (created by SceneView)

I was able to trace it back to this line (I think at least): Login @ Login.js:16

It would be this part of the code:

export function Login({navigation}){
if (auth.currentUser) {
navigation.navigate(&#39;Root&#39;)
} else {
onAuthStateChanged(auth, (user) =&gt; {
if (user) {
navigation.navigate(&quot;Root&quot;)
} 
});
}

Here is the the entire component that appears to have the bad setState. I can't seem to figure out how to get this error to go away. All the code seems to be working ok, though...

export function Login({ navigation }) {
if (auth.currentUser) {
navigation.navigate(&quot;Root&quot;);
} else {
onAuthStateChanged(auth, (user) =&gt; {
if (user) {
navigation.navigate(&quot;Root&quot;);
}
});
}
let [errorMessage, setErrorMessage] = React.useState(&quot;&quot;);
let [email, setEmail] = React.useState(&quot;&quot;);
let [password, setPassword] = React.useState(&quot;&quot;);
let login = () =&gt; {
if (email !== &quot;&quot; &amp;&amp; password !== &quot;&quot;) {
signInWithEmailAndPassword(auth, email, password)
.then((userCredential) =&gt; {
// Signed in
navigation.navigate(&quot;Home&quot;, { user: userCredential.user });
// ...
})
.catch((error) =&gt; {
setErrorMessage(error.message);
});
}
};
return (
&lt;View style={AppStyles.loginContainer}&gt;
&lt;KeyboardAvoidingView
style={AppStyles.backgroundCover}
behavior={Platform.OS === &quot;ios&quot; ? &quot;padding&quot; : null}
keyboardVerticalOffset={60}
&gt;
&lt;View style={AppStyles.loginScreen}&gt;
&lt;Text style={AppStyles.textHeader}&gt;Login&lt;/Text&gt;
&lt;Text style={AppStyles.errorText}&gt;{errorMessage}&lt;/Text&gt;
&lt;TextInput
style={AppStyles.input}
placeholder=&quot;Email&quot;
placeholderTextColor={&quot;#fff&quot;}
value={email}
onChangeText={setEmail}
/&gt;
&lt;TextInput
style={AppStyles.input}
placeholder=&quot;Password&quot;
placeholderTextColor={&quot;#fff&quot;}
secureTextEntry={true}
passwordRules={{ required: true, minLength: 6 }}
value={password}
onChangeText={setPassword}
/&gt;
&lt;View style={AppStyles.rowContainer}&gt;
&lt;Text style={AppStyles.text}&gt;Don&#39;t have an account? &lt;/Text&gt;
&lt;TextButton
size={&quot;20px&quot;}
text={&quot;Sign Up&quot;}
color={&quot;#fff&quot;}
onPress={() =&gt; navigation.navigate(&quot;Signup&quot;)}
/&gt;
&lt;/View&gt;
&lt;View style={AppStyles.rowContainer}&gt;
&lt;Text style={AppStyles.text}&gt;Forgot your password? &lt;/Text&gt;
&lt;TextButton
size={&quot;20px&quot;}
text={&quot;Reset&quot;}
color={&quot;#fff&quot;}
onPress={() =&gt; navigation.navigate(&quot;ResetPassword&quot;)}
/&gt;
&lt;/View&gt;
&lt;TextButton
size={&quot;20px&quot;}
text={&quot;Login&quot;}
backgroundColor=&quot;#83C9F4&quot;
paddingVertical={6}
paddingHorizontal={12}
onPress={login}
/&gt;
&lt;/View&gt;
&lt;/KeyboardAvoidingView&gt;
&lt;/View&gt;
);
}

答案1

得分: 2

你应该始终在进行任何导航操作之前等待组件完全挂载。

你可以尝试将导航逻辑添加到 useEffect 中:

useEffect(() => {
  if (auth.currentUser) {
    navigation.navigate('Root')
  }

  const subscriber = onAuthStateChanged(auth, (user) => {
    if (user) {
      navigation.navigate("Root")
    } 
  });

  return subscriber
}, [])
英文:

You should always wait for your component to be fully mounted before any navigation action.

Can you try to add your navigation logic into a useEffect?

useEffect(() =&gt; {
  if (auth.currentUser) {
    navigation.navigate(&#39;Root&#39;)
  }

  const subscriber = onAuthStateChanged(auth, (user) =&gt; {
    if (user) {
      navigation.navigate(&quot;Root&quot;)
    } 
  });

  return subscriber
}, [])

huangapple
  • 本文由 发表于 2023年2月24日 08:20:16
  • 转载请务必保留本文链接:https://go.coder-hub.com/75551576.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定