正文从这开始~

总览

当我们尝试在react router的Router上下文外部使用useNavigate 钩子时,会产生"useNavigate() may be used only in the context of a Router component"警告。为了解决该问题,只在Router上下文中使用useNavigate 钩子。

下面是一个在index.js文件中将React应用包裹到Router中的例子。

// index.js
import {createRoot} from 'react-dom/client';
import App from './App';
import {BrowserRouter as Router} from 'react-router-dom'; const rootElement = document.getElementById('root');
const root = createRoot(rootElement); // ️ wrap App in Router root.render(
<Router>
<App />
</Router>
);

useNavigate

现在,你可以在App.js文件中使用useNavigate钩子。

// App.js
import React from 'react';
import {
useNavigate,
} from 'react-router-dom'; export default function App() {
const navigate = useNavigate(); const handleClick = () => {
// ️ navigate programmatically
navigate('/about');
}; return (
<div>
<button onClick={handleClick}>Navigate to About</button>
</div>
);
}

会发生错误是因为useNavigate钩子使用了Router组件提供的上下文,所以它必须嵌套在Router里面。

用Router组件包裹你的React应用程序的最佳位置是在你的index.js文件中,因为那是你的React应用程序的入口点。

一旦你的整个应用都被Router组件所包裹,你可以随时随地的在组件中使用react router所提供的钩子。

Jest

如果你在使用Jest测试库时遇到错误,解决办法也是一样的。你必须把使用useNavigate钩子的组件包裹在一个Router中。

// App.test.js
import {render} from '@testing-library/react';
import App from './App';
import {BrowserRouter as Router} from 'react-router-dom'; // ️ wrap component that uses useNavigate in Router test('renders react component', async () => {
render(
<Router>
<App />
</Router>,
); // your tests...
});

useNavigate钩子返回一个函数,让我们以编程方式进行路由跳转,例如在一个表单提交后。

我们传递给navigate函数的参数与<Link to="/about">组件上的to属性相同。

replace

如果你想使用相当于history.replace()的方法,请向navigate函数传递一个配置参数。

// App.js
import {useNavigate} from 'react-router-dom'; export default function App() {
const navigate = useNavigate(); const handleClick = () => {
// ️ replace set to true
navigate('/about', {replace: true});
}; return (
<div>
<button onClick={handleClick}>Navigate to About</button>
</div>
);
}

当在配置对象中将replace属性的值设置为true时,浏览器历史堆栈中的当前条目会被新的条目所替换。

换句话说,由这种方式导航到新的路由,不会在浏览器历史堆栈中推入新的条目。因此如果用户点击了回退按钮,并不会导航到上一个页面。

这是很有用的。比如说,当用户登录后,你不想让用户能够点击回退按钮,再次回到登录页面。或者说,有一个路由要重定向到另一个页面,你不想让用户点击回退按钮从而再次重定向。

你也可以使用数值调用navigate 函数,实现从历史堆栈中回退的效果。例如,navigate(-1)就相当于按下了后退按钮。

React报错之useNavigate() may be used only in context of Router的更多相关文章

  1. react 报错的堆栈处理

    react报错 Warning: You cannot PUSH the same path using hash history 在Link上使用replace 原文地址https://reactt ...

  2. sqlplus 连接数据库报错SP2-0642: SQL*Plus internal error state 2130, context 0:0:0

    sqlplus 连接数据库报错SP2-0642: SQL*Plus internal error state 2130, context 0:0:0 问题描述: 使用sqlplus客户端登录数据库,报 ...

  3. 部署Maven项目到tomcat报错:java.lang.ClassNotFoundException: org.springframework.web.context.ContextLoaderListener【转】

    部署Maven项目到tomcat报错:java.lang.ClassNotFoundException: org.springframework.web.context.ContextLoaderLi ...

  4. eclipse使用maven,启动工程tomcat报错:java.lang.ClassNotFoundException: org.springframework.web.context.Contex

    maven是个不错的管理jar包工具,但是我们在eclipse使用maven时,总是遇上这样那样的问题,比如今天,我编译工程,启动过后,tomcat报错:java.lang.ClassNotFound ...

  5. sqlplus连接数据库报错SP2-0642: SQL*Plus internal error state 2130, context 0:0:0解决

    sqlplus连接数据库报错SP2-0642: SQL*Plus internal error state 2130, context 0:0:0解决 sqlplus 连接数据库报错SP2-0642: ...

  6. React报错 :browserHistory doesn't exist in react-router

    由于版本问题,React中history不可用 import { hashHistory } from 'react-router' 首先应该导入react-router-dom包: import { ...

  7. react报错 TypeError: Cannot read property 'setState' of undefined

    代码如下: class test extends Component { constructor(props) { super(props); this.state = { liked: false ...

  8. React报错之Cannot find name

    正文从这开始~ .tsx扩展名 为了在React TypeScript中解决Cannot find name报错,我们需要在使用JSX文件时使用.tsx扩展名,在你的tsconfig.json文件中把 ...

  9. React报错之Cannot find namespace context

    正文从这开始~ 总览 在React中,为了解决"Cannot find namespace context"错误,在你使用JSX的文件中使用.tsx扩展名,在你的tsconfig. ...

随机推荐

  1. Flask表单验证

    学习内容:①判断请求方式(request.method) from flask import Flask,render_template,request app = Flask(__name__) @ ...

  2. Git技法:.gitignore、移除暂存与撤销修改

    1. .gitignore常见项目添加 1.1 .gitignore模板 .gitignore针对每个语言都有对应的模板,在GitHub创建项目时就可以选择(你可以在GitHub提供的.gitigno ...

  3. 记一次Tomcat卡死在 Deploying web application 步骤的问题

    公司有一个历史的遗留项目是传统的MVC架构的前后不分离的项目,一开始使用JDK1.7写的,后来前一阵老板说想在这个远古项目上加点功能,顺带换换皮,于是乎一帮程序员们就用JDK1.8重新翻新了一遍项目顺 ...

  4. React简单教程-2-ts和组件参数

    前言 在上一章:React 简单教程-1-组件 我们知道了 React 的组件是什么,长什么样,用 js 和 HTML 小小体验了一下组件.在这一章,我们将使用 typescript(简称 ts) 来 ...

  5. 如何在 Mac 和虚拟机上安装 macOS Big Sur、Monterey 和 Ventura

    请访问原文链接:https://sysin.org/blog/how-to-install-macos/,查看最新版.原创作品,转载请保留出处. 作者主页:www.sysin.org 名词解释: 硬件 ...

  6. 2021.04.03【NOIP提高B组】模拟 总结

    T1 题目大意:求最小的 \(n\in[0,lim]\) 使得区间 \([L,R]\) 在线段树建树 \(build(0,n)\) 的区间内 考场时想到了正解,结果推式子退错了... 其实就是从下往上 ...

  7. SQL的语法

    SQL的语法 SQL通用语法 SQL语句可以单行或多行书写,以分号(";")结尾. SQL语句可以使用空格或缩进增强可读性. MySQL数据库的SQL语句不区分大小写(建议关键字大 ...

  8. JS:Array

    js有五种基本数据类型:string,number,boolean,null,undefined 一种引用类型,包括:1.Object类型:2.Function类型:3.Array类型:4.RegEx ...

  9. 线程池:ThreadPoolExcutor源码阅读

    ThreadPoolExcutor源码流程图:(图片较大,下载再看比较方便) 线程池里的二进制奥秘 前言: 线程池的五种状态state(RUNNING.SHUTDOWN.STOP.TIDYING.TE ...

  10. centos系统和Ubuntu系统命令区别以及常见操作

    目录 一.前言 二.系统环境 三.命令区别 3.1 使用习惯和命令区别 3.2 服务管理的区别 3.3 软件包信息区别 四.Ubuntu系统常见操作 4.1 Ubuntu系统apt和apt-get的区 ...