4
votes

I am having problems with authentication when trying to access my Windows Azure Storage Account via the REST Api.

I have read the following resources to determine how to generate the request:

http://msdn.microsoft.com/en-us/library/windowsazure/dd179428.aspx

http://convective.wordpress.com/2010/08/18/examples-of-the-windows-azure-storage-services-rest-api/

Azure Blob Service REST API returns 403 error: "Request date header not specified"

From my understanding there are only 4 variables in the request: The actual URI to determine the service endpoint, The current date in GMT time The Primary Access Key The account name.

I have the first two from the MSDN resources and the other two from my Windows Azure Portal.

GET http://<account_name>.table.core.windows.net/ HTTP/1.1
x-ms-date: Sun, 24 Feb 2013 09:19:31 GMT
x-ms-version: 2009-09-19
Authorization: SharedKey <account_name>:<primary_key>
Accept-Charset: UTF-8
Accept: application/atom+xml,application/xml
DataServiceVersion: 1.0;NetFx
MaxDataServiceVersion: 1.0;NetFx
Host: <account_name>.table.core.windows.net

I checked to ensure account name and primary key are correct and that the x-ms-date timestamp is within 15 minutes based on the suggestion from the other post.

I receive the following response:

HTTP/1.1 403 Server failed to authenticate the request. Make sure the value of Authorization header is formed correctly including the signature.
Content-Length: 437
Content-Type: application/xml
Server: Microsoft-HTTPAPI/2.0
x-ms-request-id: d78c2c11-8699-4737-9592-82813eac356e
Date: Sun, 24 Feb 2013 21:20:03 GMT

<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<error xmlns="http://schemas.microsoft.com/ado/2007/08/dataservices/metadata">
  <code>AuthenticationFailed</code>
  <message xml:lang="en-US">Server failed to authenticate the request. Make sure the value of Authorization header is formed correctly including the signature.
RequestId:d78c2c11-8699-4737-9592-82813eac356e
Time:2013-02-24T21:20:03.2036675Z</message>
</error>

Any suggestions on fixing the request to Authenticate properly?

Also, I was able to download the Azure Storage Explorer utility and access the service that way so I know the Storage Account is valid and working.

5

5 Answers

4
votes

After some more searching I found the following articles:

  1. http://msdn.microsoft.com/en-us/library/windowsazure/dd135720.aspx
  2. http://blog.einbu.no/2009/08/authenticating-against-azure-table-storage/

The basic conclusion is that SharedKeyLite must be used for this type of request.

On resource #1 it says:

The Table service requires that each request be authenticated. Both Shared Key and Shared Key Lite authentication are supported. Shared Key authentication is more secure and is recommended for requests made against the Table service using the REST API. The Microsoft .NET Client Library for WCF Data Services supports Shared Key Lite authentication only.

One resource #2 it explains how to create the ShareKeyLite and at the bottom mentions:

Since SharedKey is more robust than SharedKeyLite, that would be the obvious choice. However, we still need the SharedKeyLite scheme to access the Development Table Storage, since it is the only one that it accepts. (As of the July CTP of the Windows Azure SDK.)

1
votes

I had same problem. I downloaded Azure Storage Explorer utility too. And I was using Fiddler Web Debugger to look at requests from the utitlity to azure. Requests were like this:

GET http://mystorageaccount.table.core.windows.net/Tables() HTTP/1.1
User-Agent: Microsoft ADO.NET Data Services
DataServiceVersion: 1.0;NetFx
MaxDataServiceVersion: 2.0;NetFx
x-ms-version: 2009-09-19
x-ms-date: Tue, 26 Feb 2013 07:18:04 GMT
Authorization: SharedKeyLite mystorageaccount:mystorageaccountkey
Accept: application/atom+xml,application/xml
Accept-Charset: UTF-8
Host: mystorageaccount.table.core.windows.net
1
votes

I hit here for the same error AuthenticationFailed. For table service, this error does not give any details. Only with trial and error and seeing code snippets from other net & doing diff with what I have - is the way to debug this.

For blob service, I had seen errors which mentioned - server computed StringToSign (with value) and stringToSign from signature, do not match. That helped me fix the code computing the authentication header.

more details along with error code in rest api, will always help developer.

Coming back to the issue, the problem was that x-ms-date header was required instead of 'Date' header. So, the error code was misplaced.

For winjs windows store app. working code looked something like this:

var url = 'https://<storageaccount>.table.core.windows.net/<table name>()';
var date = new Date().toGMTString().replace('UTC', 'GMT');
var xhrOptions = {
    type: 'GET',
    url: url,
    headers: {
        // Date: date, // does not work and raises AuthenticationFailed error
        'x-ms-date' : date, // works
        'Content-Type': 'application/atom+xml',
        'x-ms-version': '2009-09-19',
        DataServiceVersion: '1.0;NetFx',
        MaxDataServiceVersion: '1.0;NetFx',
    },
};

xhrOptions.headers.Authorization = computeAuthorizationHeader(xhrOptions);
0
votes

The Authorization string needs to signed according to this spec http://msdn.microsoft.com/en-us/library/windowsazure/dd179428.aspx

Specifically the section of your header that says

<primary_key>

Should be the output of something like

Base64(HMAC_SHA256(UTF8("<primary_key>"),UTF8("VERB\n\n\nDATE\nRESOURCE")))
0
votes

You can use the solution mentioned here.

One thing to mention when you are accessing azure table"Shared Key" should be used and in case of "Blob" "SharedKey Lite is Used"

http://social.msdn.microsoft.com/Forums/en-US/windowsazureconnectivity/thread/84415c36-9475-4af0-9f52-c534f5681432

And also remember one thing if your are working behind the proxy just check that the port are not blocked. If some of the ports are blocked than there will be no response from windows azure.