IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> JavaScript知识库 -> CORS和JSONP跨域资源共享 -> 正文阅读

[JavaScript知识库]CORS和JSONP跨域资源共享

使用Express写接口

1.创建基本服务器

// 引入 express 模块
const express = require(`express`)

// 实例化express服务器
const jojo = express()

// 引入自己的路由模块
const router = require(`./apiRot.js`)

// 注册路由模块
jojo.use(`/user`, router)

//在3000接口开启服务器
jojo.listen(3000, () => {
    console.log(`服务器启动于http://127.0.0.1:3000`);
})

2.创建API路由模块

//引入express模块
const express = require(`express`)

//实例化路由对象
const router = express.Router()

//配置 express.urlencoded 中间件
router.use(express.urlencoded({ extended: false }))

// 编写get接口
router.get(`/get/:age`, (req, res) => {
    //通过req.params对象,可以访问到URL中通过 : 匹配到的动态参数.
    const qur = req.params
    
    res.send({
        status: 0, //0 表示成功 1 表示失败
        message: `GET请求成功!`, // 状态描述
        data: qur // 响应给客户端的数据
    })
})

router.get(`/get`, (req, res) => {
    //通过req.query对象,可以访问到客户端通过查询字符串形式发送到客户端的参数
    const qur = req.query

    res.send({
        status: 0, //0 表示成功 1 表示失败
        message: `GET请求成功!`, // 状态描述
        data: qur // 响应给客户端的数据
    })
})


router.post(`/post`, (req, res) => {
    //获取客户端通过请求体,发送到服务器的 URL-encoded 数据
    const body = req.body
    res.send({
        status: 0, //0 表示成功 1 表示失败
        message: `POST请求成功!`, // 状态描述
        data: body // 响应给客户端的数据
    })
})

//向外暴露router对象
module.exports = router

如果要获取URL-encoded格式的请求体数据,必须配置中间件?app.use(express.urlencoded({ extended: false }))

以上代码在未解决跨域的情况下直接使用会在浏览器控制台报跨域的错误!!!!

解决办法的方案有两种:

1.CORS(主流方案,推荐)

2.JSONP(有缺陷,只支持GET请求)

使用CORS中间件解决跨域

先介绍CORS方法:

cors 是 Express 的一个第三方中间件。通过安装和配置 cors 中间件,可以很方便地解决跨域问题。 使用步骤分为如下 3 步:

① 运行 npm install cors 安装中间件

② 使用 const cors = require('cors') 导入中间件

③ 在路由之前调用 app.use(cors()) 配置中间件

至于什么是CORS,详情可见下面的博客:链接如下

http://www.ruanyifeng.com/blog/2016/04/cors.html

CORS请求分类

客户端在请求 CORS 接口时,根据请求方式和请求头的不同,可以将 CORS 的请求分为两大类,分别是:

①简单请求

  • 同时满足以下两大条件的请求,就属于简单请求:

  • ① 请求方式:GET、POST、HEAD 三者之一

  • ② HTTP 头部信息不超过以下几种字段:无自定义头部字段、Accept、Accept-Language、Content-Language、DPR、 Downlink、Save-Data、Viewport-Width、Width 、Content-Type(只有三个值application/x-www-form-urlencoded、multipart/form-data、text/plain)

②预检请求

  • 只要符合以下任何一个条件的请求,都需要进行预检请求:

  • ① 请求方式为 GET、POST、HEAD 之外的请求 Method 类型

  • ② 请求头中包含自定义头部字段

  • ③ 向服务器发送了 application/json 格式的数据

在浏览器与服务器正式通信之前,浏览器会先发送 OPTION 请求进行预检,以获知服务器是否允许该实际请求,所以这一 次的 OPTION 请求称为“预检请求”。服务器成功响应预检请求后,才会发送真正的请求,并且携带真实数据。

简单请求和预检请求的区别

简单请求的特点:客户端与服务器之间只会发生一次请求

预检请求的特点:客户端与服务器之间会发生两次请求,OPTION 预检请求成功之后,才会发起真正的请求

JSONP跨域资源共享

首先,JSONP不属于真正的ajax请求,它是通过script标签的src属性来请求服务器上的数据,同时服务器响应一个函数调用携带数据,这种请求方式叫JSONP.

特点:

① JSONP 不属于真正的 Ajax 请求,因为它没有使用 XMLHttpRequest 这个对象。

② JSONP 仅支持 GET 请求,不支持 POST、PUT、DELETE 等请求。

使用JSONP接口的注意事项:

如果项目中已经配置了CORS,为了防止冲突,必须在CORS中间件之前声明JSONP接口,不然JSONP接口就会被解析成CORS接口!

JSONP跨域资源共享

首先,JSONP不属于真正的ajax请求,它是通过script标签的src属性来请求服务器上的数据,同时服务器响应一个函数调用携带数据,这种请求方式叫JSONP.

特点:

① JSONP 不属于真正的 Ajax 请求,因为它没有使用 XMLHttpRequest 这个对象。

② JSONP 仅支持 GET 请求,不支持 POST、PUT、DELETE 等请求。

使用JSONP接口的注意事项:

如果项目中已经配置了CORS,为了防止冲突,必须在CORS中间件之前声明JSONP接口,不然JSONP接口就会被解析成CORS接口!

实现JSONP接口的步骤

//
app.get(`/jsonp`, (req, res) => {
     //获取服务器返回的回调函数的名字
    const { callback } = req.query
    
    //返回给服务器的数据
    const obj = {
        uname: `卢本伟`,
        age: 18,
        sex: `男`
    }
   // JSON.stringify(obj)因为浏览器只能接收字符串,所以把数据转化成json格式的字符串 以函数调用的方式返回给客户端
    res.send(`${callback}(${JSON.stringify(obj)})`)
})

html中调用ajax函数,发送jsonp请求:

$(`#jsonp`).on(`click`, function () {
        $.ajax({
            method: `get`,
            dataType: `jsonp`,//一定要写,表示要发起jsonp请求!!!
            url: `http://127.0.0.1:3000/user/jsonp`,
            success: (res) => {
                console.log(res);
            }
        })
    })

成功会在控制台打印如下信息:

?

  JavaScript知识库 最新文章
ES6的相关知识点
react 函数式组件 & react其他一些总结
Vue基础超详细
前端JS也可以连点成线(Vue中运用 AntVG6)
Vue事件处理的基本使用
Vue后台项目的记录 (一)
前后端分离vue跨域,devServer配置proxy代理
TypeScript
初识vuex
vue项目安装包指令收集
上一篇文章      下一篇文章      查看所有文章
加:2021-10-11 17:25:59  更:2021-10-11 17:28:18 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/24 0:00:27-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码