Reactv19 已经发布 beta 版本,想要快速体验如何升级到 v19 版本尝鲜的朋友们可以查阅进行了解
前言
React 已于近日发布了 v19
的 beta 版本,同时为了帮助后续的 v19
升级,也同时发布了 v18.3.0
的正式版, 与 v18.2
版本完全相同,但添加了弃用 API 的警告和其他为 React 19 所需的更改
安装
使用新版 JSX Transform
为了改善打包体积和可以在 JSX 文件中无需手动引入 React
,在 2020 年 React 引入了新的 JSX Transform。如果在 React 19 中没有使用这个新的 JSX Transform 会有一个报错提示
如果已经使用了新版 JSX Transform 则可以忽略此步骤
安装最新版本的 React 和 ReactDom
npm install react@beta react-dom@beta
如果使用 TypeScript,则还需要更新相关类型包。等到 React 19 发布 release 版本后可以就像往常一样从@types/react
和@types/react-dom
安装类型包。在当前 beta 版本中需要在package.json
为类型包配置overrides
锁定版本以确保不同包中的类型是可用的
{
"dependencies": {
"@types/react": "npm:types-react@beta",
"@types/react-dom": "npm:types-react-dom@beta"
},
"overrides": {
"@types/react": "npm:types-react@beta",
"@types/react-dom": "npm:types-react-dom@beta"
}
}
Breaking changes
render 过程中的错误不再二次抛出
在之前的 React 版本中,渲染过程中抛出的错误会被捕获并重新抛出。在 DEV 模式下,我们还会记录到 console.error,导致出现重复的错误日志。
在 React 19 中,改进了错误处理方式,通过不重新抛出来减少重复信息:
- 未捕获的错误:未被错误边界捕获的错误将调用给
window.reportError
- 已捕获的错误:被错误边界捕获的错误将报告将调用给
console.error
这个改变不应该影响大多数应用,但如果生产错误报告依赖于错误被重新抛出,则可能需要更新错误处理。为了支持这一点,React 19 添加了新的createRoot
和hydrateRoot
用于自定义错误处理:
const root = createRoot(container, {
onUncaughtError: (error, errorInfo) => {
// ... log error report
},
onCaughtError: (error, errorInfo) => {
// ... log error report
}
});
废弃 React API 移除
移除propTypes
和函数组件的defaultProps
propTypes
是用于运行时校验组件 props 的属性,在 Reactv15.5.0
已经被标记为废弃,在 v19
这个正式删除
另外函数组件的defaultProps
也已经移除(使用 ES6 默认参数替代),由于 class 组件没有相应的 ES6 语法替代因此仍会保留
// Before
import PropTypes from 'prop-types';
function Heading({text}) {
return <h1>{text}</h1>;
}
Heading.propTypes = {
text: PropTypes.string,
};
Heading.defaultProps = {
text: 'Hello, world!',
};
// After
interface Props {
text?: string;
}
function Heading({text = 'Hello, world!'}: Props) {
return <h1>{text}</h1>;
}
移除使用contextTypes
和getChildContext
的 Legacy Context
Legacy Context 在2018.10(v16.6.0)已被弃用
Legacy Context 仅适用于使用contextTypes
和getChildContext
API 的类组件,并由于易于忽略的微妙错误而被contextType
替换。在 React 19 中,将删除 Legacy Context 以使 React 更小更快。仍在类组件中使用 Legacy Context,则需要迁移到新的contextType
API:
// Before
import PropTypes from 'prop-types';
class Parent extends React.Component {
//...
static childContextTypes = {
foo: PropTypes.string.isRequired,
};
getChildContext() {
return {
foo: 'bar' };
}
//...
render() {
return <Child />;
}
}
class Child extends React.Component {
//...
static contextTypes = {
foo: PropTypes.string.isRequired<