当前位置: 首页 > 知识库问答 >
问题:

使用第4版授权签名从浏览器直接上传到S3

曹高阳
2023-03-14

我需要直接从浏览器上传一个文件到S3。开始时,我创建了一个脚本,该脚本正在工作,但为了授权,我需要将我的凭据accessKeyId和secretAccessKey放入其中,这是不安全的。

我发现我可以使用“授权签名”进行授权

这看起来不错,但我找不到在upload()方法中将此授权头放在请求的何处。

我的授权标头示例:

授权:AWS4-HMAC-SHA256凭证=/20151016//s3/AWS4\U请求,SignedHeaders=内容类型;主办x-amz-date,签名=4EEE344A71A58623 FEBC4079024A27CB62F3D26546695422244FCEFE50D0168D

谢谢你的建议。

共有2个答案

宇文航
2023-03-14

您可以随POST请求附上已签名的策略文档,以便使用AWS签名版本4进行安全身份验证。

如果您在节点上,则可以使用服务器上的aws-s3-form包生成客户端所需的必要表单数据,以便向s3发送成功的请求。

你可能想阅读我关于这个主题的博客文章,以获得全面的见解。

let AwsS3Form = require('aws-s3-form')

[...]

// A hapi.js server route
server.route({
  method: ['GET',],
  path: '/api/s3Settings',
  config: {
    auth: 'session',
    handler: (request, reply) => {
      let {key,} = request.query

      let keyPrefix = `u/${request.auth.credentials.username}/`
      let region = process.env.S3_REGION
      let s3Form = new AwsS3Form({
        accessKeyId: process.env.AWS_ACCESS_KEY,
        secretAccessKey: process.env.AWS_SECRET_ACCESS_KEY,
        region,
        bucket,
        keyPrefix,
        successActionStatus: 200,
      })
      let url = `https://s3.${region}.amazonaws.com/${bucket}/${keyPrefix}${key}`
      let formData = s3Form.create(key)
      reply({
        bucket,
        region,
        url,
        fields: formData.fields,
      })
    },
  },
})
let R = require('ramda')

let ajax = require('./ajax')

class S3Uploader {
  constructor({folder,}) {
    this.folder = folder
  }

  send(file) {
    let key = `${this.folder}/${file.name}`
    return ajax.getJson(`s3Settings`, {key,})
      .then((s3Settings) => {
        let formData = new FormData()
        R.forEach(([key, value,]) => {
          formData.append(key, value)
        }, R.toPairs(s3Settings.fields))
        formData.append('file', file)

        return new Promise((resolve, reject) => {
          let request = new XMLHttpRequest()
          request.onreadystatechange = () => {
            if (request.readyState === XMLHttpRequest.DONE) {
              if (request.status === 200) {
                resolve(s3Settings.url)
              } else {
                reject(request.responseText)
              }
            }
          }

          let url = `https://s3.${s3Settings.region}.amazonaws.com/${s3Settings.bucket}`
          request.open('POST', url, true)
          request.send(formData)
        })
      }, (error) => {
        throw new Error(`Failed to receive S3 settings from server`)
      })
  }
}
宋臻
2023-03-14

我已经找到了解决这个问题的办法。我的解决方案基于此站点的示例。

在最终的解决方案中,我不使用javascript SDK,而是使用post表单和授权输入以及post参数发送的内容。

 类似资料:
  • 此文档似乎有问题:http://docs.aws.amazon.com/AmazonS3/latest/API/sigv4-authentication-HTTPPOST.html 我一丝不苟地遵循它,它似乎确实奏效了。我总是收到签名不匹配错误。v2授权仍然有效。让我想知道这是否是某种阿尔法阶段质量的产品。 下面是我的php代码。我试图模仿本页中的示例:http://docs.aws.amazon

  • 是否可以创建一个html表单,允许Web用户直接将文件上传到azure blob store,而不使用其他服务器作为中介?S3和GAW blob store都允许这样做,但我找不到对azure blob存储的任何支持。

  • 但是,没有关于如何完成这一点的例子。此外,如果没有设置凭据,即使在向S3请求上载之前,SDK也会出错 JS SDK文档中提到了这一点,因此似乎有可能:

  • 问题内容: 因此,我在将文件直接上传到S3时遇到了一些麻烦。目前,我的流程是向nodejs / express请求以获取签名的URL。 然后,我的角度控制器尝试使用该签名的URL($ scope.uploadDocument())直接上传到s3。 我的html表单看起来像 但是,每当我尝试上传到S3时,都会出现错误 我知道S3CORS在该存储桶的亚马逊端已正确设置,因为我已经开发了将相同存储桶用于

  • 我试过XMLHttpRequest的PUT请求。有一个浏览器端的限制,不允许我上传大于2GB的文件。然后我尝试了一个不需要Javascript端预处理的超文本标记语言表单的POST请求。它在一次操作中有5GB的上传大小限制。 AWS建议在较大的上传场景中进行多部分上传。这需要将文件分成小块,然后上传成小块。当文件大小大于10GB时,如何从浏览器中正确地执行此操作。

  • 我已经实现了一个使用基本身份验证(使用Spring Security性)的web服务器。 我在访问URL时禁用了默认身份验证入口点(它只返回401,而不是用www身份验证标头响应401),目的是防止浏览器显示身份验证弹出窗口。 我能够用javascript代码和命令行工具(如curl)连接到服务器,但是当我用浏览器(chrome)测试它时 <代码>curl-v-u用户:密码本地主机:8080/用户