在Postman中使用Blob服务API PUT blob - 授权标头

时间:2017-02-25 23:12:42

标签: api azure azure-storage-blobs

我需要帮助构建授权标头以PUT一个块blob。

PUT \ n \ n \ n \ n \ n \ n \ n \ n \ n \ n \ n \ nx-ms-blob-type:BlockBlob \ nx-ms-date:2017年2月25日星期六22: 20:13 GMT \ nx-ms-version:2015-02-21 \ n / myaccountname / mycontainername / blob.txt \ n

我接受这个,UTF 8编码。然后我在我的Azure帐户中使用我的访问密钥,并使用密钥将HMF sha256这个UTF 8编码的字符串。然后我在base64输出。让我们调用此输出字符串。

我的授权标题如下所示:SharedKey myaccountname:output string

它不起作用。

Postman中的标题也有x-ms-blob-type,x-ms-date,x-ms-version,Content-Length和Authorization。现在的身体说你好世界。

任何人都可以帮我在邮递员中提出这个成功的要求吗?

<?xml version="1.0" encoding="utf-8"?>
<Error>
    <Code>AuthenticationFailed</Code>
    <Message>Server failed to authenticate the request. Make sure the value of Authorization header is formed correctly including the signature.
RequestId:cdeb9a5e-0001-0029-5fb5-8f7995000000
Time:2017-02-25T22:22:32.0300016Z</Message>
    <AuthenticationErrorDetail>The MAC signature found in the HTTP request 'jiJtirohvi1syXulqkPKESnmQEJI4GpDU5JBn7BM/xY=' is not the same as any computed signature. Server used following string to sign: 'PUT


11

text/plain;charset=UTF-8






x-ms-date:Sat, 25 Feb 2017 22:20:13 GMT
x-ms-version:2015-02-21
/myaccountname/mycontainername/blob.txt'.</AuthenticationErrorDetail>
</Error>

编辑:

首先,我要感谢你和所有回复的人。我真的很欣赏它。我有最后一个问题,然后我想我会被设置!!我没有使用该代码 - 我手动完成这一切。如果我有我的密钥:X2iiy6v47j1jZZH5555555555zzQRrIAdxxVs55555555555av8uBUNGcBMotmS7tDqas14gU5O / w ==为了匿名而略有改变 - 我是否解码它:使用在线base64decoder。然后,当我的字符串现在看起来像这样:PUT \ n \ n \ n11 \ n \ ntext / plain; charset = UTF-8 \ n \ n \ n \ n \ n \ n \ nx-ms-blob -type:BlockBlob \ nx-ms-date:Mon,27 Feb 2017 21:53:13 GMT \ nx-ms-version:2015-02-21 \ n / myaccount / mycontainer / blob.txt \ n所以我运行这个在https://mothereff.in/utf-8中,然后在HMAC中使用我的解码密钥:https://www.liavaag.org/English/SHA-Generator/HMAC/ - 最后使用sha256和base64。这是我如何得到正确的字符串放在这里:SharedKey myaccount:

2 个答案:

答案 0 :(得分:1)

我认为您在此处指定StringToSign的方式存在问题:

  

PUT \ n \ n \ N11 \ n \ n \ n \ n \ n \ n \ n \ n \ NX-MS-团块型:BlockBlob \ NX-MS-日期:星期六,   2017年2月25日22:20:13   GMT \ NX-MS-版本:2015年2月21日\ N / myaccountname / mycontainername / blob.txt \ n

如果您注意到服务器返回的错误消息,则服务器签名的字符串与您的不同,不同之处在于服务器在签名计算中使用Content-Typetext/plain;charset=UTF-8)不。请在您的代码中包含此内容类型,事情应该可以正常工作。

以下是我使用的示例代码(仅部分):

        var requestMethod = "PUT";
        var urlPath = "test" + "/" + "myblob.txt";
        var storageServiceVersion = "2015-12-11";
        var date = DateTime.UtcNow.ToString("R", CultureInfo.InvariantCulture);
        var blobType = "BlockBlob";
        var contentBytes = Encoding.UTF8.GetBytes("Hello World");
        var canonicalizedResource = "/" + accountName + "/" + urlPath;
        var canonicalizedHeaders = "x-ms-blob-type:" + blobType + "\nx-ms-date:" + date + "\nx-ms-version:" + storageServiceVersion + "\n";
        var stringToSign = requestMethod + "\n" +
            "\n" + //Content Encoding
            "\n" + //Content Language
            "11\n" + //Content Length
            "\n" + //Content MD5
            "text/plain;charset=UTF-8" + "\n" + //Content Type
            "\n" + //Date
            "\n" + //If - Modified - Since
            "\n" + //If - Match
            "\n" + //If - None - Match
            "\n" + //If - Unmodified - Since
            "\n" + //Range +
           canonicalizedHeaders +
           canonicalizedResource;
        string authorizationHeader = GenerateSharedKey(stringToSign, accountKey, accountName);


    private static string GenerateSharedKey(string stringToSign, string key, string account)
    {
        string signature;
        var unicodeKey = Convert.FromBase64String(key);
        using (var hmacSha256 = new HMACSHA256(unicodeKey))
        {
            var dataToHmac = Encoding.UTF8.GetBytes(stringToSign);
            signature = Convert.ToBase64String(hmacSha256.ComputeHash(dataToHmac));
        }
        return string.Format(CultureInfo.InvariantCulture, "{0} {1}:{2}", "SharedKey", account, signature);
    }

答案 1 :(得分:0)

根据您的错误消息,它表明授权签名不正确。

如果标题中未包含Content-Type "text/plain; charset=UTF-8",请将其添加到stringTosign和postman中。

当我们尝试获取签名时,我们需要确保length of the blob.txt与stringTosign中的Content length匹配。这意味着请求主体长度应与stringTosign中的内容长度相匹配。

我用Postman测试它,它工作正常。我们可以使用另一个SO Thread中的代码获取签名。以下是我的详细步骤

  1. 添加以下标题
  2. enter image description here

    1. 添加请求正文(例如:Hello World)
    2. enter image description here

      1. 发送put blob请求。
      2. enter image description here

        更新:

        请尝试使用online tool生成测试签名。