简体   繁体   English

React 17.0.1:无效的钩子调用。 钩子只能在 function 组件的主体内部调用

[英]React 17.0.1: Invalid hook call. Hooks can only be called inside of the body of a function component

Very new react user here.非常新的反应用户在这里。 I have been troubleshooting this error for hours now.我已经解决这个错误几个小时了。 I previously had this component working as a class, but it seems everyone is migrating towards functional components lately, so I'm trying to convert it.我以前有这个组件作为 class 工作,但最近似乎每个人都在向功能组件迁移,所以我正在尝试转换它。 I did an intermediate conversion without using state and it worked fine, but I am having trouble converting username and password to state values.我在不使用 state 的情况下进行了中间转换,它工作正常,但我无法将用户名和密码转换为 state 值。

When I use the following code, I get an error:当我使用以下代码时,出现错误:

Uncaught Error: Invalid hook call. Hooks can only be called inside of the body of a function component. This could happen for one of the following reasons:
1. You might have mismatching versions of React and the renderer (such as React DOM)
2. You might be breaking the Rules of Hooks
3. You might have more than one copy of React in the same app
See https://reactjs.org/link/invalid-hook-call for tips about how to debug and fix this problem.

I have read through the linked troubleshooting page multiple times, and tried fixing all three possible causes with no success.我已多次阅读链接的故障排除页面,并尝试修复所有三个可能的原因,但均未成功。

  1. I am using react 17.0.1 and react-dom 17.0.1 in my devDependencies .我在我的 devDependencies 中使用react 17.0.1 和react-dom devDependencies
  2. I have installed the eslint-plugin-react-hooks rule to identify if I am not using hooks correctly in my functional component.我已经安装了eslint-plugin-react-hooks规则来识别我是否在我的功能组件中没有正确使用钩子。
  3. I have used npm ls react and npm ls react-dom to confirm I do not have duplicate react versions.我已经使用npm ls reactnpm ls react-dom来确认我没有重复的反应版本。

LoginForm.jsx登录表单.jsx

import React, { useEffect, useState } from 'react';
import PropTypes from 'prop-types';
const $ = require('jquery');

const LoginForm = ({ onToken }) => {

    const [username, setUsername] = useState('');
    const [password, setPassword] = useState('');

    const submit = (event) => {
        // DO NOT POST PARAMS
        event.preventDefault();
        // AJAX username and password
        const loginData = {
            username: username,
            password: password
        };
        const options = {
            url: 'api/login',
            type: 'POST',
            contentType: 'application/json; charset=utf-8',
            dataType: 'json',
            data: JSON.stringify(loginData),
            success: (data) => {
                console.log(data);
                onToken(data.token);
            }
        };

        $.ajax(options);

        console.log('Submitted!');
    };

    return (
        <form onSubmit={submit}>
            <label htmlFor="username">Username:</label><br/>
            <input value={username} onChange={e => setUsername(e.target.value)} type="text" id="username" name="username"/><br/>
            <label htmlFor="password">Password:</label><br/>
            <input value={password} onChange={e => setPassword(e.target.value)} type="password" id="password" name="password"/><br/>
            <input type="submit" value="Login"/>
        </form>
    );
};

LoginForm.propTypes = {
    onToken: PropTypes.func
};

export default LoginForm;

I have created a branch on my project's repository so you can view any other information:我在项目的存储库上创建了一个分支,以便您查看任何其他信息:

Branch: https://github.com/GibsDev/node-password-manager/tree/login-conversion分支: https://github.com/GibsDev/node-password-manager/tree/login-conversion

Commit: https://github.com/GibsDev/node-password-manager/commit/e0714b16bdbbf339fabf1aa4f6eefacd6d053427提交: https://github.com/GibsDev/node-password-manager/commit/e0714b16bdbbf339fabf1aa4f6eefacd6d053427

You're calling this loginForm as if it was a plain function , not as a React component:你调用这个loginForm就好像它是一个普通的 function ,而不是一个 React 组件:

const loginForm = LoginForm({
    onToken: token => {
        const url = new URL(window.location.href);
        const returnurl = url.searchParams.get('returnurl');
        if (returnurl) {
            window.location.href = decodeURIComponent(returnurl);
        } else {
            window.location.href = '/';
        }
    }
});

ReactDOM.render(loginForm, domContainer);

As a result, it doesn't get wrapped in React.createElement , so it thinks the hook call is invalid.结果,它没有被包裹在React.createElement中,所以它认为钩子调用是无效的。

Use JSX syntax instead:改用 JSX 语法:

const onToken = token => {
        const url = new URL(window.location.href);
        const returnurl = url.searchParams.get('returnurl');
        if (returnurl) {
            window.location.href = decodeURIComponent(returnurl);
        } else {
            window.location.href = '/';
        }
}

ReactDOM.render(<LoginForm onToken={onToken} />, domContainer);
          //    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 React Hooks Mobx:无效的钩子调用。 钩子只能在函数组件的主体内部调用 - React Hooks Mobx: invalid hook call. Hooks can only be called inside of the body of a function component 反应钩子错误:无效的钩子调用。 钩子只能在 function 组件的主体内部调用 - React hook Error: Invalid hook call. Hooks can only be called inside of the body of a function component React Hooks + Mobx =&gt; 无效的钩子调用。 Hooks 只能在函数组件内部调用 - React Hooks + Mobx => Invalid hook call. Hooks can only be called inside of the body of a function component 反应:无效的挂钩调用。 挂钩只能在功能组件的主体内部调用 - React: Invalid hook call. Hooks can only be called inside of the body of a function component 无效的挂钩调用。 钩子只能在反应 18 中的函数组件的主体内部调用 - Invalid hook call. Hooks can only be called inside of the body of a function component in react 18 反应 useEffect 无效的钩子调用。 钩子只能在 function 组件的主体内部调用 - React useEffect Invalid hook call. Hooks can only be called inside of the body of a function component 反应路由器:无效的钩子调用。 钩子只能在 function 组件的主体内部调用 - React Router: Invalid hook call. Hooks can only be called inside of the body of a function component React Native:错误:无效的挂钩调用。 钩子只能在 function 组件的主体内部调用 - React Native: Error: Invalid hook call. Hooks can only be called inside of the body of a function component React - 无效的挂钩调用。 钩子只能在 function 组件的内部调用 - React - Invalid hook call. Hooks can only be called inside of the body of a function component React Native 错误:无效的钩子调用。 钩子只能在 function 组件的主体内部调用 - React Native Error: Invalid hook call. Hooks can only be called inside of the body of a function component
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM