如何使用 Axios 从本地主机 VueJS 调用服务器?

How to call a server from localhost VueJS with Axios?

我正在尝试从我的 VueJS 应用程序调用 AWS 托管的 API,它在我的 localhost:8080 上是 运行。我已经使用 this blog post 通过此块设置 vue.config.js

module.exports = {
    devServer: {
        proxy: 'https://0123456789.execute-api.eu-west-1.amazonaws.com/'
    },
    ...
}

有了这个,我可以使用此代码向该主机的端点发出 GET 请求:

  this.$axios
    .get('https://0123456789.execute-api.eu-west-1.amazonaws.com/mock/api/endpoint',
    {
      headers: {
        'Content-Type': 'application/json'
    }})

这是因为我已将 AWS API 网关模拟端点配置为 return 这些 headers 用于 OPTIONS 方法:

Access-Control-Allow-Headers: 'Cache-Control,Expires,Pragma,Content-Type,X-Amz-Date,Authorization,X-Api-Key,X-Amz-Security-Token'   
Access-Control-Allow-Methods: 'DELETE,GET,HEAD,OPTIONS,PATCH,POST,PUT'  
Access-Control-Allow-Origin: '*'

但是,我无法拨打这个电话:

  this.$axios
    .get('https://0123456789.execute-api.eu-west-1.amazonaws.com/lambda/api/function',
    {
      headers: {
        'Content-Type': 'application/json'
    }})

此端点是一个 Lambda 集成,也有一个 OPTIONS 方法,与上面的 headers 相同。

为什么配置相同的两个端点对 axios 的响应不同?

更新

根据@deniz 的建议,我更新了 .env.development 文件以包含:

VUE_APP_API_URI=https://0123456789.execute-api.eu-west-1.amazonaws.com/

我还将 axios 请求更新为:

let url = 'mock/api/endpoint'
let headers = {
  headers: {
    'Content-Type': 'application/json',
  },
}

this.$axios
  .get(url, headers)

...和...

let url = 'lambda/api/function'
let headers = {
  headers: {
    'Content-Type': 'application/json',
  },
}

this.$axios
  .get(url, headers)

第一个 GET 请求得到的结果是:

200 OK

但是第二个请求的响应是:

Access to XMLHttpRequest at 'https://0123456789.execute-api.eu-west-1.amazonaws.com/lambda/api/function' from origin 'http://localhost:8080' has been blocked by CORS policy: Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource.

您的开发环境配置。作为代理设置,什么都不做然后假装是别人。 这就是为什么在使用代理时不会遇到任何 CORS 问题的原因。它有点瓶颈,就像“我是别人,不是本地主机”

module.exports = {
    devServer: {
        proxy: 'https://0123456789.execute-api.eu-west-1.amazonaws.com/'
    },
    ...
}

从现在开始,您的所有请求都来自这个非常基于代理的 URL

https://0123456789.execute-api.eu-west-1.amazonaws.com/

如果您尝试像这样访问 api:

this.$axios
    .get('https://0123456789.execute-api.eu-west-1.amazonaws.com/lambda/api/function',
    {
      headers: {
        'Content-Type': 'application/json'
    }})

你应该记住,你已经假装你的代理正在做他的伪装工作并且仍然像来自其他来源的代理一样。

当你调用 API 时你的 URL 现在看起来像这样,如果我没有完全错的话:

https://0123456789.execute-api.eu-west-1.amazonaws.com/https://0123456789.execute-api.eu-west-1.amazonaws.com/lambda/api/function

您只需将请求中的 axios url 更改为:

this.$axios
    .get('lambda/api/function',
    {
      headers: {
        'Content-Type': 'application/json'
    }})

然后重试。


更新

VUE_APP_API_URI=https://0123456789.execute-api.eu-west-1.amazonaws.com/

将您的 URL 字符串用引号括起来,像这样并删除最后一个斜杠。

VUE_APP_API_URI='https://0123456789.execute-api.eu-west-1.amazonaws.com'

这是处理 .env 变量的常见做法。

2。 您收到的 CORS 错误是不再使用代理的结果。 您现在从其他来源请求数据,这在 FireFox 或 Chrome 等现代浏览器上是不允许的

此处您必须在 API 中处理服务器端配置: https://0123456789.execute-api.eu-west-1.amazonaws.com

因为如果你这样做,你需要给你的本地主机和你的后端处理请求的权限,如果请求是从不同的来源发出的,就像你的情况一样:

我是 localhost,我向 https://0123456789.execute-api.eu-west-1.amazonaws.com

请求数据

通常这是被禁止的,并且存在很高的安全风险

但是解决办法是... 正如您之前在 AWS API 中所做的那样 Access-Control-Allow-Origin: '*' 是处理“CORS”问题的重要部分。

确保它设置正确并且按预期工作。也许玩弄它并设置 localhost 而不是 * (允许所有)

3。 我强烈建议您在开发中使用代理方式,仅在生产中使用非代理方式,并且只允许您的前端使用 CORS。