关于解决跨域的几种方式

一、为什么会出现跨域

因为浏览器存在着一个安全功能-同源策略原因导致的。当协议、域名、端口号三者有一个不相同时,就会出现跨域。

二、IP地址、域名、端口号的关系

常见的IP地址分为IPv4与IPv6两大类。目前我们使用的都是IPv4的地址,IPv4地址由32位二进制数组成,常以XXX.XXX.XXX.XXX形式表现。(以上参考于维基百科) IP地址其实就代表着唯一的一台主机。

通常客户端会输入域名(原因之一是IP地址太难记了),通过DNS将域名解析成服务器IP地址,从而访问网站。

端口号是对应一台主机上的多个服务。一台主机对应一个IP,但一个主机上可提供多个服务,每个服务都有一个端口号。

参考链接:网站的域名和端口

三、解决跨域

重点来了!!!
下面我们介绍一下如何解决跨域吧,这里主要介绍三种方式:

1、跨域资源共享(CORS)

只服务端设置Access-Control-Allow-Origin即可,前端无需设置,若要带cookie请求,则前后端都需要设置。

// 设置响应头的中间件
module.exports = async (ctx, next) => {
  const contentType = 'application/json; charset=utf-8'
  ctx.set('Content-Type', contentType)
  // 跨域,添加底下这个即可实现跨域
  ctx.set("Access-Control-Allow-Origin", "*") 
  ctx.set("Access-Control-Allow-Methods", "OPTIONS, GET, PUT, POST, DELETE")
  await next()
}

2、JSONP

创建一个js文件:

var express = require('express');

// 90端口的服务,将当前目录作为http服务
var app = express()
app.use(express.static(__dirname))
app.listen(90)

// 91端口的服务,返回数据
var app2 = express()
// jsonp有一个缺点是只能用于get方式
app2.get('/', function(req, res){
	var funcname = req.query.callback;
	res.send(funcname+"('你好')")
	// f('你好')
})
app2.listen(91)

在html文件中:

DOCTYPE html>
<html>
<body>
	<h1>helloh1>
	<script>
		function f(data) {
			alert(data)
		}
	script>
	// script中href、src等不存在跨域问题,只有通过ajax请求才存在跨域问题,jsonp就是通过这个原理
	<script src="http://localhost:91?callback=f">script>
body>
html>

参考链接:CORS和JSONP跨域

3、node中间件代理跨域(vue框架)

前提是项目使用vue-cli搭建的,修改的配置文件是vue.config.js

  • 项目根目录创建vue.config.js文件
  • 添加devServer配置项,配置里边的proxy
module.exports = {
	devServer: {
		proxy: {
			'/api': {         //  /api表示拦截以/api开头的请求路径 
				target: 'https://www.vue-js.com/api',     // 跨域的域名(一般不需要写路径),这里以vue网址举例,一般只需要写https://www.vue-js.com
				// ws: true,        //  是否代理websocked
				changeOrigin: true,   // 是否开启跨域 
				pathRewrite: {        // 重写路径
					'^/api': ''       // 把/api变成空字符
				}
			}
		}
	}
}

在vue页面中:

<button @click"handleClick">跨域请求</button>

...

methods: {
	handlerClick() {
		// 跨域开启后,会拦截以/api开头的请求路径,并将域名替换成https://www.vue-js.com/api/api/v1/topics,通过pathRewrite属性将/api换成空字符串,最终请求的路径就变成https://www.vue-js.com/api/v1/topics
		axios.get('/api/v1/topics').then(res => {
			console.log(res)
		})
	}
}


参考链接:使用vue.config.js解决跨域

自己对跨域一直含糊不清,所以总结出来,嘿嘿~
有不对的地方欢迎指正,欢迎留言~

你可能感兴趣的:(JavaScript,node.js)