前情提要

日常工作中,我们会使用fetch,或者axios发起请求来获取数据,但是当我们遇到一些特殊需求的时候,使用不同库之后,会得到不同的结果,例如302,308的状态码,那么我们应该怎么处理这两种情况呢?

下面我将会手把手教你实现:

如何使用多种方案实现前端代码+302后端接口实现页面跳转?fetch 发送GET 或者 POST请求如何处理 302?或者是说fetch 怎么才能拦截302?Axios 响应拦截 302 状态码的方案有哪些?如何实现?

基础环境准备

使用简单代码启动一个简单的nodejs后端

初始化项目

npm init

安装依赖

npm install express cors --save

模拟几个302请求

根目录下创建app.js文件,我们模拟一些302请求

var express = require("express");

var app = express();

const cors = require("cors");

//跨域请求cors

app.use(

cors({

origin: "*",

credentials: true,

})

);

// code 200 请求

app.get("/success", function (req, res) {

res.send("ok");

});

app.post("/success", function (req, res) {

res.send("ok");

});

// code 500 请求

app.get("/error500", function (req, res) {

res.sendStatus(500);

});

const urlInfo = {

baidu: "https://www.baidu.com/",

error: "http://localhost:3002/error500", // 这个接口会返回状态码500

notFound: "http://localhost:3002/notfound", // 根本就没有这个接口

success: "http://localhost:3002/success", // 200

};

app.get("/redirect-success", function (req, res) {

res.redirect(302, urlInfo.success);

});

app.post("/redirect-success", function (req, res) {

res.redirect(302, urlInfo.success);

});

app.get("/redirect-baidu", function (req, res) {

res.redirect(302, urlInfo.baidu);

});

app.post("/redirect-baidu", function (req, res) {

res.redirect(302, urlInfo.baidu);

});

app.get("/redirect-error", function (req, res) {

res.redirect(302, urlInfo.error);

});

app.post("/redirect-error", function (req, res) {

res.redirect(302, urlInfo.error);

});

app.get("/redirect-not-found", function (req, res) {

res.redirect(302, urlInfo.notFound);

});

app.post("/redirect-not-found", function (req, res) {

res.redirect(302, urlInfo.notFound);

});

var http = app.listen(3002, "127.0.0.1", function () {

var httpInfo = http.address();

console.log(`创建服务${httpInfo.address}:${httpInfo.port}成功`);

});

注意事项

下述状态码,我只试了302,大家可以自行修改后端代码测试其他状况哦~~

重定向状态码: 301: Moved Permanently 302: Found 303: See Other 307: Temporary Redirect 308: Permanent Redirect

启动http服务

node app.js

或者是使用supervisor来进行服务端代码热更新

supervisor使用方式(建议使用它来启动代码)

npm官方文档Node Supervisor用于在程序崩溃时重新启动程序。它还可以用于在*.js文件更改时重新启动程序。

npm install supervisor -g

supervisor app.js

启动成功

接口测试

前端准备

我这里用vue来举例子啦~~,其他框架都一样哦~~

创建项目

npm create vue@latest

下载依赖

cd 项目名

npm install

启动项目

npm run dev

准备基础页面

功能1:如何使用前端代码+302后端接口实现页面跳转?

方案1 - window.location.assign(当前页跳转)

我们在项目中添加以下代码

方案2 - window.open(新页面打开,或者当前页打开,可以自己控制参数)

核心代码如下:(详细代码将会在后面全部粘贴出来)

window.open(urlInfo.baidu, '_blank');

方案3 - window.location.href

核心代码如下:(详细代码将会在后面全部粘贴出来)

window.open(urlInfo.baidu, '_blank');

功能1总体代码

功能2:fetch 发送GET 或者 POST请求如何处理 302?或者是说fetch 怎么才能拦截302?

我们使用模拟的几个url来进行几种情况的展示,然后根据返回结果,大家就知道如何处理302情况了哦`

情况1:

情况2:

切换URL

我们来分析一下这种情况,302重定向的URL是返回500的url,此时我们可以得到重定向后的结果,这个时候我们就有办法处理啦~

情况3:

切换URL

情况4:

更改URL为200情况

const urlInfo = {

baidu: 'http://localhost:3002/redirect-baidu',

error: 'http://localhost:3002/redirect-error',

notFound: 'http://localhost:3002/redirect-not-found',

success: 'http://localhost:3002/redirect-success',

}

const currentUrl = urlInfo.success

总结

使用Fetch,302重定向的目标URL跨域的情况下,我们无法获取此时的请求具体信息,只能在catch里拿到报错结果使用Fetch, 302重定向的目标URL返回状态码200,404,500的情况下,我们可以通过res.redirected准确得知此时接口是重定向,以及通过后端接口返回的res.url得到准确的重定向URL综上所述,重定向目标URL正常的情况下,我们使用Fetch可以成功响应拦截 302 状态码,以及做后续的逻辑处理,因为cors的情况非常容易处理,使用代理等其他配置完全可以避免此种情况。

功能3:axios 发送GET 或者 POST请求如何处理 302?Axios 响应拦截 302 状态码的方案有哪些?如何实现?

下载依赖

npm i axios --save

编写基础代码

情况1:

const currentUrl = urlInfo.success

情况2:

跨域的情况下,会走catch,然后得到Network Error的报错提示语

{

"message": "Network Error",

"name": "AxiosError",

"stack": "AxiosError: Network Error\n at XMLHttpRequest.handleError (http://localhost:5173/node_modules/.vite/deps/axios.js?v=e7c1b0b9:1451:14)",

"config": {

"transitional": {

"silentJSONParsing": true,

"forcedJSONParsing": true,

"clarifyTimeoutError": false

},

"adapter": [

"xhr",

"http"

],

"transformRequest": [

null

],

"transformResponse": [

null

],

"timeout": 0,

"xsrfCookieName": "XSRF-TOKEN",

"xsrfHeaderName": "X-XSRF-TOKEN",

"maxContentLength": -1,

"maxBodyLength": -1,

"env": {},

"headers": {

"Accept": "application/json, text/plain, */*"

},

"method": "get",

"url": "http://localhost:3002/redirect-baidu"

},

"code": "ERR_NETWORK",

"status": null

}

情况3:

情况4:

结论

我们打印一下统一的返回数据

{

"message": "Request failed with status code 500",

"name": "AxiosError",

"stack": "AxiosError: Request failed with status code 500\n at settle (http://localhost:5173/node_modules/.vite/deps/axios.js?v=e7c1b0b9:1204:12)\n at XMLHttpRequest.onloadend (http://localhost:5173/node_modules/.vite/deps/axios.js?v=e7c1b0b9:1421:7)",

"config": {

"transitional": {

"silentJSONParsing": true,

"forcedJSONParsing": true,

"clarifyTimeoutError": false

},

"adapter": [

"xhr",

"http"

],

"transformRequest": [

null

],

"transformResponse": [

null

],

"timeout": 0,

"xsrfCookieName": "XSRF-TOKEN",

"xsrfHeaderName": "X-XSRF-TOKEN",

"maxContentLength": -1,

"maxBodyLength": -1,

"env": {},

"headers": {

"Accept": "application/json, text/plain, */*",

"Content-Type": "application/json"

},

"method": "post",

"url": "http://localhost:3002/redirect-error",

"data": "{\"method\":\"post\"}"

},

"code": "ERR_BAD_RESPONSE",

"status": 500

}

使用Axios,302重定向的目标URL跨域的情况下,我们无法获取此时的请求具体信息,只能在catch里拿到报错结果,报错显示信息使用Axios, 302重定向的目标URL返回状态码200的情况下,我们可以通过res.request.responseURL与res.config.url进行比对来准确得知此时接口是否重定向,以及通过后端接口返回的res.request.responseURL,以及如果重定向的url是html页面的话,我们加上判断headers[“content-type”]类型是否包含text/html得到准确的重定向URL使用Axios, 302重定向的目标URL返回状态码404,500的情况下,我们可以通过catch 里 捕获 error.request.responseURL与error.config.url进行比对来准确得知此时接口是否重定向,以及通过后端接口返回的error.request.responseURL,以及如果重定向的url是html页面的话,我们加上判断headers[“content-type”]类型是否包含text/html得到准确的重定向URL综上所述,重定向目标URL正常的情况下,我们使用Axios可以成功响应拦截 302 状态码,以及做后续的逻辑处理,因为cors的情况非常容易处理,使用代理等其他配置完全可以避免此种情况。

分析图示

代码

代码仓库

今天就写到这里啦~

小伙伴们,( ̄ω ̄( ̄ω ̄〃 ( ̄ω ̄〃)ゝ我们明天再见啦~~大家要天天开心哦

欢迎大家指出文章需要改正之处~ 学无止境,合作共赢

欢迎路过的小哥哥小姐姐们提出更好的意见哇~~

相关阅读

评论可见,请评论后查看内容,谢谢!!!
 您阅读本篇文章共花了: