node.js ajax数据请求跨域问题

最近想用node作为后台抛出接口,前端页面去请求接口的时候报错了,发现是跨域的问题。为什么会出现跨域问题呢?我们就需要了解什么是浏览器的同源策略。
什么是浏览器的同源策略,为什么要同源策略

同源策略简单来说就是三同,同协议、同域名、同端口。个域内的脚本仅仅具有本域内的权限,可以理解为本域脚本只能读写本域内的资源,而无法访问其它域的资源。这种安全限制称为同源策略,有同源策略的原因就在于为了提升浏览器的安全性,但是,我们都知道安全性和方便性是成反比的,有了高的安全性必定给我们的操作带来低效,牺牲了Web拓展上的灵活性,现代浏览器在安全性和可用性之间选择了一个平衡点。在遵循同源策略的基础上,选择性地为同源策略“开放了后门”。例如img、script 、style等标签,都允许垮域引用资源,严格说这都是不符合同源要求的。

JavaScript这个安全策略在进行多iframe或多窗口编程、以及Ajax编程时显得尤为重要。根据这个策略,在souhu.com下的页面中包含的JavaScript代码,不能访问在google.com域名下的页面内容;甚至不同的子域名之间的页面也不能通过JavaScript代码互相访问。对于Ajax的影响在于,通过XMLHttpRequest实现的Ajax请求,不能向不同的域提交请求,例如,在you.example.com下的页面,不能向me.example.com提交Ajax请求,等等。

举例说明
URL 说明 是否允许通信
http://www.baidu.com/a.js
http://www.baidu.com/b.js
同一域名 允许
http://www.baidu.com/map/a.js
http://www.baidu.com/tieba/b.js
同一域名不同文件夹下 允许
http://www.baidu.com:8000/a.js
http://www.baidu.com/b.js
同一域名不同端口 不允许
http://www.baidu.com/a.js
https://www.baidu.com/b.js
同一域名不同协议 不允许
http://www.baidu.com/a.js
http://75.32.68.45/b.js
域名和域名对应ip 不允许
http://www.baidu.com/a.js
http://query.baidu.com/b.js
主域相同,子域不同 不允许
http://www.baidu.com/a.js
http://www.google.com/b.js
不同域名 不允许
为什么浏览器要实现同源限制?我们举例说明:

比如一个黑客,他利用iframe把真正的银行登录页面嵌到他的页面上,当你使用真实的用户名和密码登录时,如果没有同源限制,他的页面就可以通过javascript读取到你的表单中输入的内容,这样用户名和密码就轻松到手了。又比如你登录了淘宝,同时浏览了恶意网站,如果没有同源限制,该恶意 网站就可以构造AJAX请求频繁在淘宝发广告帖.

这是前端页面显示的错误
//前端页面报错内容
Failed to load http://localhost:3000/users/login: Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://localhost' is therefore not allowed access.
//服务端错误方法
// node登录接口,文件地址routes/users.js
router.post('/login',function (req, res, next) {
    // 打印post请求的数据内容
    console.log(req.body);
    console.log(req.body.username);
    console.log(req.body.password);
    if (req.body.username == "shuah" && req.body.password == "123456") {
        res.end(JSON.stringify(dataSuccess));
    } else {
        res.end(JSON.stringify(dataError));
    }
});
//前端数据请求
//引用jquery.js
var data ={
      username:'shuah',
      password:'123456'
}
$.ajax({
  url: "http://localhost:3000/users/login",
  type: "POST",
  headers:{
    "Conten-Type":"http://localhost:3000/users/login"
    },
  data: JSON.stringify(data),
  dataType:"json",
  success: function(data){
    console.info("success.");
    console.log(data)
  }
})

总结了两个解决node跨域的方法。

  1. 简单粗暴,但是任何页面都可以请求,不安全。
//在每个方法的头部加入
res.header("Access-Control-Allow-Origin", "*");
res.header("Access-Control-Allow-Headers", "X-Requested-With");
res.header("Access-Control-Allow-Methods","PUT,POST,GET,DELETE,OPTIONS");
res.header("X-Powered-By",' 3.2.1');
res.header("Content-Type", "application/json;charset=utf-8");
// login 方法修改为
router.post('/login',function (req, res, next) {
  res.header("Access-Control-Allow-Origin", "*");
  res.header("Access-Control-Allow-Headers", "X-Requested-With");
  res.header("Access-Control-Allow-Methods","PUT,POST,GET,DELETE,OPTIONS");
  res.header("X-Powered-By",' 3.2.1');
  res.header("Content-Type", "application/json;charset=utf-8");
  // 打印post请求的数据内容
  console.log(req.body);
  console.log(req.body.username);
  console.log(req.body.password);
  if (req.body.username == "shuah" && req.body.password == "123456") {
      res.end(JSON.stringify(dataSuccess));
  } else {
      res.end(JSON.stringify(dataError));
  }
});
//前端页面
$.ajax({
  url: "http://localhost:3000/users/login",
  type: "POST",
  data:data,
  dataType:"json",
  success: function(data){
      console.info("success.");
      console.log(data)

  }
})

2.引入 cors 安全,自定义

npm install cors

cors的githbu地址,里面有更加多的方法 https://github.com/expressjs/cors

//相对与上一个方法,这个不用每个方法都添加请求头
//在app.js里面修改
var cors = require('cors')
app.use(cors())
//自定义设置
//在app.js里面修改,只有http://localhost可以访问请求,其他都为跨域,安全,需要启动一个本地服务
var cors = require('cors')
app.use(cors({
    origin:['http://localhost'],
    methods:['GET','POST'],
    alloweHeaders:['Conten-Type', 'Authorization']
}));

//前端页面
$.ajax({
  url: "http://localhost:3000/users/login",
  type: "POST",
  data:data,
  dataType:"json",
  success: function(data){
    console.info("success.");
    console.log(data)
  }
})

猜你喜欢

转载自blog.csdn.net/weixin_36934930/article/details/79298097