创建钩子时真的需要导入'React'吗? (反应钩子)
Posted
技术标签:
【中文标题】创建钩子时真的需要导入\'React\'吗? (反应钩子)【英文标题】:Do you really need to import 'React' when creating hooks? (React-hooks)创建钩子时真的需要导入'React'吗? (反应钩子) 【发布时间】:2019-11-07 09:42:43 【问题描述】:我看到了https://reactjs.org/docs/hooks-custom.html 他们总是这样做的例子:
import React, useState, useEffect from 'react';
但是React
并没有真正用在文件中,我们真的需要它吗?为什么?
我问这个问题是因为我遇到了 eslint 的问题:
'React' is defined but never used no-unused-vars
- 我正在使用 create-react-app 3.0.1,其中 eslint 已包含在内 - (我不确定如何解决此问题 - 已经尝试过 this 并尝试将其添加到包中.json eslintConfig
但仍然没有)
【问题讨论】:
“但 React 并没有真正在文件中使用”如果你的代码中有 jsx,它实际上是被使用的。如果不是,您只能导入钩子,例如,如果您的代码包含自定义钩子定义并且本身不涉及元素创建。 【参考方案1】:如果要渲染JSX
,则需要React
。
为避免出现eslint
警告,您应该使用eslint-plugin-react 中的react-in-jsx-scope 规则。
在该规则中,它还解释了为什么在文件中需要React
,即使你不使用它(你认为你不使用它,但如果你渲染JSX
,你会这样做)。
使用 JSX 时,
<a />
扩展为React.createElement("a")
。因此 React 变量必须在范围内。 如果您使用@jsx pragma,则此规则将检查指定变量而不是 React 变量。
【讨论】:
hmmm 我对我的组件使用相同的规则,它没有抱怨,它只抱怨钩子文件。 (无论如何都接受了答案,因为它解释了为什么我需要导入 React,这是这个问题的标题) 在钩子文件上,你输入React
,然后它会给出警告,在其他组件中,你可能在class Foo extends React.Component
中使用React
@IamL 期望什么?
它会在钩子文件上抛出警告(回到上面的问题)?
@IamL 是的。你有 2 条规则。一个说,no-unused-vars
,这会运行你的代码并检查代码中是否使用了变量。 react-in-jsx-scope
将寻找React
并检查您是否使用JSX
,如果是,它将覆盖no-unused-vars
的React
变量,因为它知道稍后,JSX
将使用变量React
和它转译。 no-unused-vars
不知道你会转译你的代码并在以后使用React
。【参考方案2】:
React 17 有一个新的 JSX 转换,它不再需要导入(也向后移植到新版本 16.14.0、15.7.0 和 0.14.10)。你可以在这里读更多关于它的内容: https://reactjs.org/blog/2020/09/22/introducing-the-new-jsx-transform.html
// no import needed
const App = () => <div>hello!</div>
但是,您仍然需要导入才能使用钩子:
import useState from 'react'
const App = () =>
const [stuff, setStuff] = useState('stuff')
return <div>stuff</div>
文档还链接到脚本以自动更新项目中的所有文件以修复所有导入。就我个人而言,我习惯于只使用React.useWhatever
表单,因此我不需要弄乱导入语句,但使用命名导入可能会减少最终包的大小。
文档说命名导入现在是推荐的方式,所以不推荐这样做,但如果你真的想保留 React
导入,你可以设置下面的 eslint 规则来阻止它抱怨。请注意,这将继续在所有文件中使用它。
"react/jsx-uses-react": "error"
【讨论】:
【参考方案3】:来自 React 官方文档:
从根本上说,JSX 只是为
React.createElement(component, props, ...children)
函数。 JSX 代码:
<MyButton color="blue" shadowSize=2>Click Me</MyButton>
编译 进入:
React.createElement(MyButton, color: 'blue', shadowSize: 2,'Click Me' )
你也可以使用标签的自闭合形式,如果 没有孩子。所以:
<div className="sidebar" />
编译成:
React.createElement('div', className: 'sidebar', null )
https://reactjs.org/docs/jsx-in-depth.html
EDIT Hooks 也在 React 命名空间下,React.useState ...等
【讨论】:
您的回答适用于文件中有JSX的情况,但是在OP引用的自定义钩子示例中,文件中没有JSX。以上是关于创建钩子时真的需要导入'React'吗? (反应钩子)的主要内容,如果未能解决你的问题,请参考以下文章