js实现跨域的几种方法汇总(图片ping、JSONP和CORS)

yizhihongxing

概述

跨域是指在同源策略限制下,客户端无法向不同源(协议、域名、端口)的服务器发送请求。但有些情况下需要跨域请求,这时可以使用以下几种方法:图片ping、JSONP和CORS。

方法一:图片ping

通过创建一个HTML的日志资源文件来达到跨域目的,将数据转化为图片地址,然后请求这个图片地址。

<img src="http://example.com/?data=[data]" />

这样发送是不会中止请求的,即使服务器不支持任何的输出形式。

优缺点:
- 优点:对浏览器兼容性要求较低,一般都可以完成跨域操作。
- 缺点:只能使用 GET 请求方式,并且无法设置请求头,只能从服务器拿到请求成功或失败的结果,且不能获得服务端返回的数据。

方法二:JSONP

JSONP 全称为 JSON with Padding,简单来说就是在js里面执行函数,为什么要用padding呢?因为 JSONP其实是利用<script>标签来实现的,可以被普通的浏览器进行跨域访问的特性,这种格式的数据很难实现由 JSON 转译成 JSONP,因此使用了这种 hack 的方式。padding其实是指要在服务端将JSON数据填入到一对用户定义的函数调用中(函数名在URL中),从而构成JS文件(JSONP文件)。

假设客户端需要从 http://example.com/?callback=func 这个URL获取数据,并且要求接口返回的数据格式为 callback(data)

function func(data) {
  console.log(data)
}

const script = document.createElement('script')
script.src = 'http://example.com/?callback=func'
document.head.append(script)

在这个js文件中,会向服务器发送一个 URL 请求,并且 URL 中包含一个名为callback的参数,这个参数的值就是要获得 JSON 数据之后要立即调用的函数名,在服务器端将数据放进其中,并返回这个 js 文件内容,客户端浏览器接收到这个js文件之后,会自动执行func(data)函数。

优缺点:
- 优点:能跨域请求跨域数据,不受同源策略限制,支持 GET 请求,可以向服务端发送请求时设置请求头。
- 缺点:只支持 GET 请求,并且必须判断响应的数据格式,需要服务端配合,且容易受到XSS攻击。

方法三:CORS

CORS 全称为 Cross-Origin Resource Sharing,是 HTML5 提供的一种机制,采用额外的 HTTP 头来告诉浏览器,以允许 Web 应用程序访问不属于其来源的选定资源,浏览器会对复杂请求(例如:get/post以及POST的两种Content-Type:application/json,application/x-www-form-urlencoded)发起一次预检,可以看做是一次请求前置确认,服务器返回“METHOD,Origin,Accept-language,Accept”等字段,携带带校验信息,让浏览器放行实际的请求。

在服务器端,需要添加如下响应头:

Access-Control-Allow-Origin: http://example.com
Access-Control-Allow-Methods: POST,GET,OPTIONS
Access-Control-Max-Age: 1000
Access-Control-Allow-Headers: Content-Type, Authorization

在客户端,直接发送 AJAX 请求,浏览器会自动在请求头中添加Origin字段发起预检请求,如果服务器支持跨域,会返回以上响应头信息。

const xhr = new XMLHttpRequest()
xhr.open('POST', 'http://example.com/api')
xhr.setRequestHeader('Content-Type', 'application/json')
xhr.setRequestHeader('Authorization', 'Bearer ' + token)
xhr.onreadystatechange = function () {
  if (xhr.readyState === 4 && xhr.status === 200) {
    console.log(xhr.responseText)
  }
}
xhr.send(JSON.stringify({data: 'some data'}))

优缺点:
- 优点:绝大多数浏览器都支持,以标准化的请求头、状态码、请求方法来对跨域请求和响应进行规范,同时支持 GET/POST 等请求方式。
- 缺点:需要服务器端进行配置,在某些第三方库中并不支持 CORS。

示例一

通过JSONP方式从服务器获取数据。

服务端随意设置一个接口,返回数据。

const express = require('express')
const app = express()

app.get('/jsonp', (req, res) => {
  const callback = req.query.callback
  const data = {a: 1, b: 2, c: 3}
  res.send(`${callback}(${JSON.stringify(data)})`)
})

app.listen(3000, () => console.log('listening on port 3000'))

客户端通过JSONP跨域获取数据,代码如下所示:

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>JSONP Demo</title>
</head>
<body>
  <script>
    function handleData(data) {
      console.log(data)
    }

    const script = document.createElement('script')
    script.src = 'http://localhost:3000/jsonp?callback=handleData'
    document.head.append(script)
  </script>
</body>
</html>

示例二

通过CORS方式从服务器获取数据。

服务端随意设置一个接口,返回数据。

const express = require('express')
const app = express()

app.use((req, res, next) => {
  res.header('Access-Control-Allow-Origin', '*')
  res.header('Access-Control-Allow-Methods', 'GET,POST,OPTIONS')
  res.header('Access-Control-Allow-Headers', 'Origin,Content-Type,Authorization')
  next()
})

app.post('/cors', (req, res) => {
  const data = req.body
  res.json(data)
})

app.listen(3000, () => console.log('listening on port 3000'))

客户端通过 AJAX 跨域获取数据,代码如下所示:

const xhr = new XMLHttpRequest()
xhr.open('POST', 'http://localhost:3000/cors')
xhr.setRequestHeader('Content-Type', 'application/json')
xhr.setRequestHeader('Authorization', 'Bearer ' + token)
xhr.onreadystatechange = function () {
  if (xhr.readyState === 4 && xhr.status === 200) {
    console.log(xhr.responseText)
  }
}
xhr.send(JSON.stringify({data: 'some data'}))

结语

以上三种方法均可用于跨域请求,但不同的请求方式适用于不同的场景,需要根据实际业务情况选择。而若是自身网站项目,建议使用第三种CORS方式,若要集成第三方传输库则可考虑JSONP方式。

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:js实现跨域的几种方法汇总(图片ping、JSONP和CORS) - Python技术站

(0)
上一篇 2023年5月17日
下一篇 2023年5月17日

相关文章

  • python中将函数赋值给变量时需要注意的一些问题

    在Python中,函数可以像变量一样被赋值给其他变量。这个特性使得Python在函数式编程方面非常灵活。然而,将函数赋值给变量时也需要注意一些问题,下面详细讲解了这些问题,并提供了一些示例。 1. 注意函数和变量的命名 在将函数赋值给变量时,需要注意函数名称和变量名称的区分。具体来说,不能使用函数的名称来定义变量,否则会覆盖函数,导致无法调用该函数。例如,下…

    云计算 2023年5月18日
    00
  • Python字符编码判断方法分析

    Python字符编码判断方法分析示例 简介 字符编码判断在Python编程中非常重要,因为有时我们需要处理多种字符编码的文件,如果不正确地判断字符编码,则可能会导致乱码或者其它问题。本文将详细介绍Python中判断字符编码的各种方法并给出示例。 方法一:使用chardet库 chardet是Python中一个非常流行的检测字符编码的库,可以通过pip安装。 …

    云计算 2023年5月18日
    00
  • windows2003 IIS6 部署MVC3和MVC4程序的方法

    以下是关于“Windows 2003 IIS6 部署 MVC3 和 MVC4 程序的方法”的详细攻略。 确认环境 在开始之前,我们需要确认以下环境是否满足要求:- Windows Server 2003 操作系统- 安装了 IIS6- 安装了 .NET Framework 4.0- 安装了 MVC3 或 MVC4 运行库 部署MVC应用程序 具体部署步骤如下…

    云计算 2023年5月17日
    00
  • oppo reno云空间满了怎么办?oppo reno云空间清理教程

    oppo reno云空间满了怎么办?oppo reno云空间清理教程攻略 本文将介绍oppo reno云空间满了怎么办以及oppo reno云空间清理教程的完整攻略,包括清理方法、注意事项、示例说明等。 1. oppo reno云空间满了怎么办? 当oppo reno云空间满了时,可以通过以下方法进行清理: 1.1 删除不需要的文件 在oppo reno云空…

    云计算 2023年5月16日
    00
  • Python+FuzzyWuzzy实现模糊匹配的示例详解

    接下来我将详细讲解“Python+FuzzyWuzzy实现模糊匹配的示例详解”的完整攻略。 标题 1. 简介 在实际应用中,我们经常需要对字符串进行模糊匹配。例如,我们可以根据用户输入的关键词,匹配出数据库中的所有包含该关键词的数据。这时,FuzzyWuzzy这个库就可以派上用场了。FuzzyWuzzy库是一个基于Levenshtein距离算法的模糊匹配工具…

    云计算 2023年5月18日
    00
  • ASP.NET Core 中间件的使用之全局异常处理机制

    下面是关于“ASP.NET Core 中间件的使用之全局异常处理机制”的完整攻略,包含两个示例说明。 简介 在ASP.NET Core应用程序中,我们可以使用中间件来处理HTTP请求和响应。在本攻略中,我们将介绍如何使用中间件来实现全局异常处理机制。 实现步骤 以下是使用中间件实现全局异常处理机制的步骤: 创建一个异常处理中间件: 我们可以创建一个异常处理中…

    云计算 2023年5月16日
    00
  • ASP.NET Core利用UrlFirewall对请求进行过滤的方法示例

    下面是“ASP.NET Core利用UrlFirewall对请求进行过滤的方法示例”的完整攻略。 1. 什么是UrlFirewall UrlFirewall是ASP.NET Core中的一个中间件,它可以根据一系列的规则,对请求的URL进行过滤,只允许合法的URL请求通过,而拦截并拒绝非法的URL请求。UrlFirewall的主要作用是提高应用程序的安全性。…

    云计算 2023年5月17日
    00
  • 干货:区块链相关疑问解析

    干货:区块链相关疑问解析 区块链是一种去中心化的分布式账本技术,近年来备受关注。本文将对区块链相关的疑问进行解析,包括什么是区块链、区块链的优势、区块链的应用场景等。 1. 什么是区块链? 区块链是一种去中心化的分布式账本技术,它将数据存储在多个节点上,每个节点都有完整的账本副本。每个区块包含了一定数量的交易记录,这些交易记录被加密后形成一个哈希值,并与前一…

    云计算 2023年5月16日
    00
合作推广
合作推广
分享本页
返回顶部