如何修复'我们计算的请求签名与签名'错误不匹配?

时间:2015-05-28 23:47:56

标签: amazon-web-services amazon-s3 aws-php-sdk

我已经在网上搜索了两天以上,并且可能查看了大多数在线记录的场景和解决方法,但到目前为止我没有任何作用。

我在运行PHP 5.3的AWS SDK for PHP V2.8.7上。我正在尝试使用以下代码连接到我的S3存储桶:

// Create a `Aws` object using a configuration file

        $aws = Aws::factory('config.php');

        // Get the client from the service locator by namespace
        $s3Client = $aws->get('s3');

        $bucket = "xxx";
        $keyname = "xxx";

        try {
            $result = $s3Client->putObject(array(
                'Bucket'        =>      $bucket,
                'Key'           =>      $keyname,
                'Body'          =>      'Hello World!'
            ));
            $file_error = false;
        } catch (Exception $e) {
            $file_error = true;
            echo $e->getMessage();
            die();
        }
        //  

我的config.php文件如下:

<?php

return array(
    // Bootstrap the configuration file with AWS specific features
    'includes' => array('_aws'),
    'services' => array(
        // All AWS clients extend from 'default_settings'. Here we are
        // overriding 'default_settings' with our default credentials and
        // providing a default region setting.
        'default_settings' => array(
            'params' => array(
                'credentials' => array(
                    'key'    => 'key',
                    'secret' => 'secret'
                )
            )
        )
    )
);

产生以下错误:

  

我们计算的请求签名与您提供的签名不符。检查您的密钥和签名方法。

我已经检查了我的访问密钥和秘密至少20次,生成了新密码,使用不同的方法传递信息(即配置文件并在代码中包含凭据)但是目前没有任何工作。

46 个答案:

答案 0 :(得分:36)

经过两天的调试,我终于发现了问题......

我分配给对象的密钥以句点..\images\ABC.jpg开头,这导致错误发生。

我希望API提供更有意义和相关的错误消息,唉,我希望这会帮助其他人!

答案 1 :(得分:16)

我使用错误的凭据收到此错误。我认为最初粘贴它时会有隐形字符。

答案 2 :(得分:10)

如果您的密钥前后有空格,似乎通常会发生此错误

答案 3 :(得分:6)

尝试复制具有某些UTF8字符的对象时遇到了同样的问题。下面是一个JS示例:

var s3 = new AWS.S3();

s3.copyObject({
    Bucket: 'somebucket',
    CopySource: 'path/to/Weird_file_name_ðÓpíu.jpg',
    Key: 'destination/key.jpg',
    ACL: 'authenticated-read'
}, cb);

通过使用encodeURIComponent()

对CopySource进行编码来解决此问题

答案 4 :(得分:5)

我遇到了同样的问题,我遇到的问题是我导入了错误的环境变量,这意味着我的 AWS 密钥错误。根据阅读所有答案,我会验证您的所有访问 ID 和密钥是否正确,并且没有其他字符或任何内容。

答案 5 :(得分:3)

在我的情况下,当我需要使用9时我正在使用s3.getSignedUrl('getObject')(因为我正在使用PUT上传我的文件),这就是签名不匹配的原因。 / p>

答案 6 :(得分:3)

实际上在Java中我得到了相同的错误。花了4个小时来调试它之后我发现问题出现在S3对象的元数据中,因为在s3文件中坐着缓存控件时有空间。这个空间被允许进入1.6。*版本但在1.11。*它是不允许的,因此抛出了签名不匹配错误

答案 7 :(得分:3)

当我故意提供了错误的具有“秘密”价值的密钥时,它给出了这个错误。我期待一些有效的错误消息详细信息,例如“身份验证失败”或其他内容

答案 8 :(得分:3)

对于Python集-signature_version s3v4

s3 = boto3.client(
   's3',
   aws_access_key_id='AKIAIO5FODNN7EXAMPLE',
   aws_secret_access_key='ABCDEF+c2L7yXeGvUyrPgYsDnWRRC1AYEXAMPLE',
   config=Config(signature_version='s3v4')
)

答案 9 :(得分:2)

我刚刚使用AWS SDK和React Native将图像上传到S3。事实证明它是由ContentEncoding参数引起的。

删除该参数&#34;修复&#34;这个问题。

答案 10 :(得分:1)

大部分时间是由于密钥错误(AWS_SECRET_ACCESS_KEY)导致的。请交叉验证您的AWS_SECRET_ACCESS_KEY。希望它能工作...

答案 11 :(得分:1)

如果其他提到的解决方案都不适合您,请尝试使用

aws configure

this command将打开一组选项,询问键,区域和输出格式。

希望这有帮助!

答案 12 :(得分:1)

尝试复制对象时出现此错误。我通过编码copySource修复了它。实际上在方法文档中对此进行了描述:

参数: copySource –源存储桶的名称和源对象的键名,以斜杠(/)分隔。必须经过URL编码。

CopyObjectRequest objectRequest = CopyObjectRequest.builder()
                .copySource(URLEncoder.encode(bucket + "/" + oldFileKey, "UTF-8"))
                .destinationBucket(bucket)
                .destinationKey(newFileKey)
                .build();

答案 13 :(得分:1)

就我而言,在AWS签名授权方法中使用邮递员发出请求时,我使用S3(大写)作为服务名称

答案 14 :(得分:1)

在调试和花费大量时间后,在我的情况下,问题出在access_key_id和secret_access_key上,请仔细检查您的凭据或生成新的凭据,并确保您在参数中传递了凭据。

答案 15 :(得分:1)

像其他人一样,我也有类似的问题,但在 java sdk v1.5 中。对我来说,以下 2 个修复对我有帮助。

  1. 我的对象键看起来像这样 /path/to/obj/。在这里,我首先删除了开头的 /
  2. 此外,仅靠第 1 点并不能解决问题。我将 sdk 版本从 1.9.x 升级到 1.11.x

应用这两个修复程序后,它起作用了。所以我的建议不是将其注销。如果没有其他工作,请尝试升级库。

答案 16 :(得分:1)

就我而言,我将S3网址解析为其组件。

例如:

Url:    s3://bucket-name/path/to/file

被解析为:

Bucket: bucket-name
Path:   /path/to/file

具有包含前导“ /”的路径部分使请求失败。

答案 17 :(得分:1)

我遇到了类似的错误,但对我来说,似乎是因为重新使用IAM用户在两个不同的Elastic Beanstalk环境中使用S3。我通过为每个环境创建一个具有相同权限的IAM用户来处理症状,这使得错误消失了。

答案 18 :(得分:0)

我的AccessKey的一些特殊字符无法正确转义。

我在复制/粘贴键时没有检查特殊字符。让我绊了几分钟。

一个简单的反斜杠修复了它。示例(显然不是我真正的访问密钥):

secretAccessKey: 'Gk/JCK77STMU6VWGrVYa1rmZiq+Mn98OdpJRNV614tM'

成为

secretAccessKey: 'Gk\/JCK77STMU6VWGrVYa1rmZiq\+Mn98OdpJRNV614tM'

答案 19 :(得分:0)

很奇怪,我之前有一个错误The authorization mechanism you have provided is not supported. Please use AWS4-HMAC-SHA256。关于Stackoverflow,有一个答案需要添加AWS_S3_REGION_NAME = 'eu-west-2' (your region)AWS_S3_SIGNATURE_VERSION = "s3v4

这样做之后,先前的错误已清除,但我再次遇到了此签名错误。搜索答案,直到最终删除AWS_S3_SIGNATURE_VERSION = "s3v4为止。将其放在这里也许会对某人有所帮助。顺便说一下,我正在使用Django。

答案 20 :(得分:0)

在我的例子中,api 调用参数的错误顺序导致了这个。

例如,当我有 /api/call1?parameter1=x¶meter2=y 时,我收到了这条消息。

“请求的签名与计算的签名不匹配。”

交换参数后:/api/call1?parameter2=y¶meter1=x api 调用按预期工作。非常令人沮丧,因为 api 文档本身的参数顺序不同。这也不是唯一发生这种情况的电话。

答案 21 :(得分:0)

我看不出有什么好的理由,删除存储桶并重新创建它对我有用。

答案 22 :(得分:0)

大多数情况是在您获取SECRET密钥并将其传递给弹性客户端时发生的。

例如: 密钥:ABCW1233 ** + OxMMMMMMM8x **

在客户端中进行配置时,您只能通过:ABCW1233 **(+号之前的部分)。

答案 23 :(得分:0)

就我而言,我不得不等待几个小时,直到将文件上传到存储桶并为其生成预先签名的URL。

答案 24 :(得分:0)

我遇到了同样的问题。导致问题的代码片段:

<iframe title="PDF Viewer" src={`${docPdfLink}&embed=true`} />

对我来说,有两个问题

  1. 在链接末尾使用 embed 会导致签名不匹配,因此,出现了问题。
  2. S3 中的文件具有除 application/pdf 以外的内容类型,因此在修复第一个点后我无法呈现 pdf。

所以,这是我在代码中所做的:

<iframe title="PDF Viewer" src={docPdfLink} />

在 s3 存储桶中:s3 file content type 此外,我们还需要确保每当我们向 s3 添加或创建 pdf 时,它都应该具有应用程序内容 application/pdf

答案 25 :(得分:0)

当〜/ .aws / credentials中的密钥周围带有引号时,我得到了这个。

aws_secret_access_key =“ KEY”

答案 26 :(得分:0)

只需添加多种显示方式即可。

如果您在iOS上使用safari,并且已连接到Safari Technology Preview控制台-您将看到相同的问题。如果您从控制台断开连接-问题将消失。

当然,这使排查其他问题变得困难,但这是100%的重复。

我正在尝试找出可以在STP中进行更改的内容,以阻止它执行此操作,但尚未找到它。

答案 27 :(得分:0)

在我的情况下,问题是用于配置Amplify的API网关URL在末尾加了一个斜杠...

查询的网址看起来像https://....amazonaws.com/myapi//myendpoint。我删除了conf中的多余斜杠,它起作用了。

这不是我一生中最明确的错误消息。

答案 28 :(得分:0)

在我的情况下,存储桶名称错误,其中包含密钥的第一部分(bucketxxx / keyxxx)-签名没有错。

答案 29 :(得分:0)

在我的情况下(python),它失败了,因为文件中有这两行代码,它们是从较旧的代码继承而来的

http.client.HTTPConnection._http_vsn = 10 http.client.HTTPConnection._http_vsn_str = 'HTTP/1.0'

答案 30 :(得分:0)

我可以通过设置环境变量来解决此问题。

export AWS_ACCESS_KEY=
export AWS_SECRET_ACCESS_KEY=

在IntelliJ + py.test中,我用[Run] > [Edit Configurations] > [Configuration] > [Environment] > [Environment variables]设置环境变量

答案 31 :(得分:0)

另一个可能的问题是,元值包含非US-ASCII字符。对我而言,在将值添加到putRequest时,它有助于对值进行UrlEncode编码:

request.Metadata.Add(AmzMetaPrefix + "artist", HttpUtility.UrlEncode(song.Artist));
request.Metadata.Add(AmzMetaPrefix + "title", HttpUtility.UrlEncode(song.Title));

答案 32 :(得分:0)

当使用Debian Stretch可用的最新awscli版本(即1.11.13版)时,我在具有非AWS S3端点的Docker映像中遇到了此问题。

升级到CLI版本1.16.84解决了该问题。

要使用基于Debian拉伸映像的Dockerfile安装最新版本的CLI,而不是:

RUN apt-get update
RUN apt-get install -y awscli
RUN aws --version

使用:

RUN apt-get update
RUN apt-get install -y python-pip
RUN pip install awscli
RUN aws --version

答案 33 :(得分:0)

我必须设置

def hi(obj):
        print("Hi, I am " + obj.name)

class Robot:
    say_hi = hi


x = Robot()
x.name = "Marvin"
Robot.say_hi(x)

在使用ruby aws sdk v2之前(在其他语言中也可能与此类似)

答案 34 :(得分:0)

对我来说,我使用axios并默认发送标头

content-type: application/x-www-form-urlencoded

所以我更改为发送:

content-type: application/octet-stream

,并且还必须将此Content-Type添加到AWS签名

const params = {
    Bucket: bucket,
    Key: key,
    Expires: expires,
    ContentType = 'application/octet-stream'
}

const s3 = new AWS.S3()
s3.getSignedUrl('putObject', params)

答案 35 :(得分:0)

在aws-php-sdk的早期版本中,在弃用S3Client::factory()方法之前,允许您放置文件路径的一部分,即Key S3Client->putObject() parameters,在bucket参数上。我使用v2 SDK在生产环境中使用了文件管理器。由于工厂方法仍然有效,因此在更新为~3.70.0之后,我没有重新访问此模块。今天,我花了两个小时的大部分时间来调试为什么我开始收到此错误,但最终由于我传递的参数(该参数过去一直起作用)而导致:

$s3Client = new S3Client([
    'profile' => 'default',
    'region' => 'us-east-1',
    'version' => '2006-03-01'
]);
$result = $s3Client->putObject([
    'Bucket' => 'awesomecatpictures/catsinhats',
    'Key' => 'whitecats/white_cat_in_hat1.png',
    'SourceFile' => '/tmp/asdf1234'
]);

我必须将存储桶/密钥路径的catsinhats部分移到Key参数,就像这样:

$s3Client = new S3Client([
    'profile' => 'default',
    'region' => 'us-east-1',
    'version' => '2006-03-01'
]);
$result = $s3Client->putObject([
    'Bucket' => 'awesomecatpictures',
    'Key' => 'catsinhats/whitecats/white_cat_in_hat1.png',
    'SourceFile' => '/tmp/asdf1234'
]);

我认为正在发生的事情是Bucket名称现在已被URL编码。在进一步检查我从SDK收到的确切消息后,我发现了这一点:

PutObject上执行https://s3.amazonaws.com/awesomecatpictures%2Fcatsinhats/whitecats/white_cat_in_hat1.png

时出错

AWS HTTP错误:客户端错误: PUT https://s3.amazonaws.com/awesomecatpictures%2Fcatsinhats/whitecats/white_cat_in_hat1.png产生了403 Forbidden

这表明我提供给/参数的Bucket已经通过urlencode(),现在是%2F

签名的工作方式相当复杂,但是问题归结为存储桶,并且使用密钥来生成加密的签名。如果它们在主叫客户端和AWS内都不完全匹配,则请求将被拒绝403。错误消息确实指出了问题:

  

我们计算出的请求签名与您的签名不匹配   提供。 检查您的密钥和签名方法。

因此,我的Key是错误的,因为我的Bucket是错误的。

答案 36 :(得分:0)

我不知道是否有人在尝试在浏览器中测试输出的URL时遇到此问题,但是您是否使用Postman并尝试从RAW选项卡复制生成的AWS URL ,因为转义了反斜杠,您将遇到上述错误。

使用Pretty标签复制并粘贴该网址,以查看其是否实际有效。

我最近遇到了这个问题,该解决方案解决了我的问题。出于测试目的,查看您是否实际上通过url检索了数据。

此答案是对那些尝试从AWS生成下载,临时链接或通常从AWS生成URL以供使用的人员的参考。

答案 37 :(得分:0)

我通过在 AWS.S3()内添加 apiVersion 解决了这个问题,然后它非常适合S3签名的URL。

更改自

var s3 = new AWS.S3();

var s3 = new AWS.S3({apiVersion: '2006-03-01'});

有关更多详细示例,请参考此AWS Doc SDK示例: https://github.com/awsdocs/aws-doc-sdk-examples/blob/master/javascript/example_code/s3/s3_getsignedurl.js

答案 38 :(得分:0)

在我的情况下,我调用s3request.promise().then()时出错,导致只执行一次调用就导致两次执行请求。

我的意思是我遍历了6个对象,但发出了12个请求(您可以通过登录控制台或在浏览器中调试网络进行检查)

由于第二个不需要的时间戳记与第一个请求的签名不符,因此产生了此问题。

答案 39 :(得分:0)

我有同样的问题。我有默认的方法,PUT设置为定义预签名的URL,但是试图执行GET。该错误是由于方法不匹配造成的。

答案 40 :(得分:0)

我在nodejs中有同样的错误。但是在s3构造函数中添加signatureVersion可以帮助我:

const s3 = new AWS.S3({
  apiVersion: '2006-03-01',
  signatureVersion: 'v4',
});

答案 41 :(得分:0)

在通过Java SDK将文档上传到CloudSearch时遇到此错误。问题是由于要上载的文档中有特殊字符。错误“我们计算出的请求签名与您提供的签名不匹配。请检查您的AWS Secret Access密钥和签名方法。”非常容易误导人。

答案 42 :(得分:0)

生成新的访问密钥对我有用。

答案 43 :(得分:0)

我通过更改AWS s3存储桶上的公共权限并在存储桶设置中添加了以下CORS配置来解决此问题。

<?xml version="1.0" encoding="UTF-8"?>
<CORSConfiguration>
<CORSRule>
    <AllowedOrigin>*</AllowedOrigin>
    <AllowedMethod>HEAD</AllowedMethod>
    <AllowedMethod>GET</AllowedMethod>
    <AllowedMethod>PUT</AllowedMethod>
    <AllowedMethod>POST</AllowedMethod>
    <AllowedHeader>*</AllowedHeader>
</CORSRule>
</CORSConfiguration>

有关更多信息,请参见AWS s3 documentation

答案 44 :(得分:0)

就像其他人所说的那样,我也遇到了同样的问题,事实证明这与密码/访问密码有关。我为s3用户生成了一个无效的密码,并且没有通知我。尝试与用户连接时,出现此错误。它似乎不喜欢密码中的某些或所有符号(至少对于Minio)

答案 45 :(得分:0)

由于以下原因,我遇到相同的错误。

我输入了正确的凭证,但有复制粘贴。这样可能会在复制粘贴时插入垃圾字符。 我已经手动输入并运行了代码,现在可以正常工作了

谢谢