Создать таблицу в Azure, используя REST API - PullRequest
0 голосов
/ 23 сентября 2018

Кто-нибудь пробовал создать таблицу внутри учетной записи хранения с использованием REST API?Я могу сделать это без проблем, если я использую авторизацию SharedKeyLite.Тем не менее, при использовании авторизации SharedKey, аутентификация продолжает сбой.

Я предполагаю, что нужно что-то делать со значением "Content-MD5" в подписи авторизации.Документация немного неопределенна в отношении значения Content-MD5, и я не могу найти рекомендуемый способ создания Content-MD5 в документации.

Я не могу найти пример с использованием C #.Единственный пример, который я нашел, - это использование Powershell, а для Content-MD5 - пустая строка.Тем не менее, это не работает для моего случая.

Вот мой код:

public static void CreateTable(string storageAccount, string storageKey, string tableName)
        {
            var client = new HttpClient();

            string date = DateTime.UtcNow.ToString("R", System.Globalization.CultureInfo.InvariantCulture);
            client.DefaultRequestHeaders.Add("x-ms-date", date);
            string msVersion = "2018-03-28";
            client.DefaultRequestHeaders.Add("x-ms-version", msVersion);
            client.DefaultRequestHeaders.Add("MaxDataServiceVersion", "3.0;NetFx");
            client.DefaultRequestHeaders.Add("DataServiceVersion", "3.0;NetFx");
            client.DefaultRequestHeaders.Add("Accept", "application/json;odata=nometadata");
            string payload = "{ \"TableName\":\""+ tableName +"\" }";
            int contentLength = GetContentLength(payload);
            string authH = "SharedKey " + storageAccount + ":" + CreateTableSignature("POST", payload, "application/json", date, storageAccount + "/Tables", storageKey, new List<string>() { });
            client.DefaultRequestHeaders.Add("Authorization", authH);
            string requestUri = $"https://{storageAccount}.table.core.windows.net/Tables";

            HttpRequestMessage request = new HttpRequestMessage(HttpMethod.Post, requestUri);
            request.Content = new StringContent(payload,
                                                Encoding.UTF8,
                                                "application/json");
            request.Content.Headers.ContentLength = contentLength;
            client.SendAsync(request)
                  .ContinueWith(responseTask =>
                  {
                      Console.WriteLine("Response: {0}", responseTask.Result);
                  });
        }
public static string CreateTableSignature(string verb, string content, string contentType,  string date, string resource, string key, List<string> canonicalizedResourceParms)
        {
            string msgSignature = verb + "\n" +
               CreateMD5(content) + "\n" +
               contentType + "\n" +
               date + "\n";

            msgSignature += "/" + resource;
            foreach (string parm in canonicalizedResourceParms)
                msgSignature += "\n" + parm;
            byte[] SignatureBytes = Encoding.UTF8.GetBytes(msgSignature);

            // Create the HMACSHA256 version of the storage key.
            HMACSHA256 SHA256 = new HMACSHA256(Convert.FromBase64String(key));

            // Compute the hash of the SignatureBytes and convert it to a base64 string.
            return Convert.ToBase64String(SHA256.ComputeHash(SignatureBytes));

        }
public static string CreateMD5(string input)
        {
            // Use input string to calculate MD5 hash
            using (System.Security.Cryptography.MD5 md5 = System.Security.Cryptography.MD5.Create())
            {
                byte[] inputBytes = System.Text.Encoding.ASCII.GetBytes(input);
                byte[] hashBytes = md5.ComputeHash(inputBytes);
                return Convert.ToBase64String(hashBytes);
            }
        }

1 Ответ

0 голосов
/ 25 сентября 2018

Две точки для исправления.

  1. Content-Type

    request.Content = new StringContent(payload,
                                        Encoding.UTF8,
                                        "application/json");
    

    В этом методе SDK фактически устанавливает application/json; charset=utf-8 при отправке запроса.Это означает, что подпись также нуждается в application/json; charset=utf-8.

    Или я рекомендую вам удалить эту вводящую в заблуждение настройку типа контента и использовать

    request.Content.Headers.ContentType = new MediaTypeHeaderValue("application/json");
    
  2. Content-MD5

    Это не требуется в подписи, вы можете оставить его пустым.В противном случае, если вы хотите поместить его в подпись, вам нужно сначала добавить соответствующий заголовок запроса.

    request.Content.Headers.ContentMD5 = Convert.FromBase64String(CreateMD5(payload));
    

    Кроме того, в методе CreateMD5 () кодировка должна быть UTF8

    System.Text.Encoding.UTF8.GetBytes(input);
    
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...