Windows Azure Internals: Trabalhando com Storage Service e API REST (parte 2)

Cloud Computing & Microsoft Azure

Figura2


 

Os primeiros passos

Antes de continuar nosso artigo, é importante repassarmos alguns termos importantes juntamente com o seu comportamento em relação ao Azure.

URL

A URL identifica o recurso que você deseja obter. No armazenamento do Windows Azure, isso normalmente inclui o nome da conta no hostname, e o recurso informado no caminho.

Headers (cabeçalhos)

Para cada requisição (request) ou resposta(response) em HTTP, temos um cabeçalho que fornece as informações necessárias sobre o pedido. Você pode se utilizar destes cabeçalhos para gerar um novo cabeçalho para permitir que o servidor valide sua origem, identificando como seu. Existem também cabeçalhos personalizados para determinadas operações. No Windows Azure Storage Service, todos os cabeçalhos personalizados tem um prefixo x-ms-.

Métodos HTTP

O método HTTP indica a ação exata a ser executada. O Windows Azure utiliza apenas os seguinte métodos:

  • GET: Recupera a representação padrão de um recurso. Para uma Queue, este é o conteúdo de uma mensagem. Para uma entidade da tabela, esta será uma versão XML da entidade, e assim por diante.
  • PUT: Cria ou atualiza um recurso. Você normalmente colocar a URL de um recurso com o corpo do pedido contendo os dados que você deseja carregar.
  • POST: É usado para atualizar os dados de uma entidade. Ele é semelhante ao PUT, diferindo apenas no fato que normalmente você espera que o recurso já existe na URL informada.
  • DELETE: Exclui o recurso especificado na URL.

Status code (Código de Status)

A especificação HTTP documenta mais de 40 códigos de status diferentes. Felizmente, você tem que se preocupar com apenas um pequeno subconjunto desses 40 códigos. Estes são usados para contar-lhe o resultado da operação-se bem sucedida ou não, e se não, uma dica a respeito de porque ele falhou. Aqui estão as principais classes de códigos de status:

  • 2xx (Está tudo OK)
    Códigos de resposta na gama 2xx geralmente significar que a operação teve êxito. Quando você criar com êxito um blob, você recebe de volta um 201, e quando você enviar um GET para um blob, você recebe de volta um 200.
  • 3xx (Não Modificado)
    No mundo web padrão, os códigos na gama 3xx são usados para controlar o cache e redirecionamento. No Azure, apenas o código 304 pode ocorrer. Quando você trabalha com um recurso, você obtém uma ETag associada a ele. Você pode pensar em uma ETag como um identificador exclusivo que especifica qual é o estado atual dos dados no servidor. Se houver alteração de dados durante a manipulação do recurso, sua ETag também vai mudar. Se você especificar uma ETag sem que o recurso tenha sido alterado, você receberá um código 304. ETags também são utilizados para implementar concorrência otimista.
  • 4xx (Bad request)
    Códigos na faixa 4xx significam que a solicitação falhou por algum motivo. Isto pode ocorrer devido cabeçalhos incorretos, URL incorreta, a conta ou recurso não existe, etc. O corpo da resposta conterá mais informações sobre o motivo da falha na resposta. Dois códigos a serem observados são 403 (informações de autenticação inválidas) e 404 (recurso inexistente).
  • 5xx (Tenso… Algo de errado aconteceu no servidor)
    Se existe um código que você não vai querer ver, serão os códigos desta faixa. Eles sinalizam que um erro desconhecido ocorreu no servidor ou o menos provável, que ele está ocupado demais para lidar com as solicitações. Caso isso aconteça, o mais provável é que você tenha solicitado um conjunto de dados muito grande e a operação expirou.

.

Codificando RESTful no Windows Azure Storage

Agora vamos iniciar a parte pesada da brincadeira, codificar nossa API de acesso ao Storage do Windows Azure. Esta não é uma coisa habitual a se fazer, a intenção e conhecer mais a fundo o funcionamento dos serviços de Storage do Azure e não focar na criação da API em si. Vamos explorar apenas alguns serviços dos blobs, queues e tables.

1º passo: Classe Base

Vamos criar uma classe base StorageAzure, contendo as constantes do cabeçalho e um construtor para instanciar as credenciais da conta no Azure. Observem que temos quatro campos para instanciarmos a conta, senha e host do serviço seja do ambiente de desenvolvimento local seja da subcription do azure, e um campo que define em que ambiente estamos trabalhando respectivamente.

Listagem1_thumb4

Com isso já é possível codificar o método RequisicaoDeArmazenamento que será responsável por montar e executar a requisição com base no recurso solicitado. Vamos observar o método RequisicaoDeArmazenamento:

Listagem2_thumb2

Primeiro criamos o pedido definindo a URI e criando a requisição. Como nossa API está flexível para trabalhar na nuvem ou utilizar o Storage Emulator, então estou fazendo uma verificação de qual ambiente está sendo utilizado para montar a URI corretamente. Informamos o método HTTP a ser trabalhado, se há dados e caso haja informa o tamanho do conteúdo e o seu tipo. Adiciona no cabeçalho a propriedade x-ms-date que é obrigatória e define o UTC(Universal Time Coordinated) para a solicitação. Adiciona as propriedades específicas do cabeçalho de solicitação e chama a rotina para assinatura da solicitação.

Existem mais dois outros métodos para criar a assinatura da requisição. Notem que existe um método específico para a assinatura da requisição quando trabalhamos com Tabelas, veremos mais detalhes no próximo passo.

 

2º passo: Assinatura

Já vimos que o serviço de armazenamento do azure é exposto via REST, já montamos nossa requisição e o cabeçalho então agora é só fazer o pedido. Certo? Bem, nós podemos mas a tarefa se torna um pouco complexo devido à necessidade de um cabeçalho de autorização válida. Quando você criar seu projeto Azure Storage, uma chave de acesso principal é criado. Esta é a chave que você usará para assinar sua mensagem. Esta mensagem assinada é passada no cabeçalho HTTP de autorização. O servidor irá usar isso para autenticar o pedido. Sem este trecho de código não será possível obter sucesso nas requisições. Mesmo tendo a URI e todos os cabeçalhos corretos, sem a assinatura e autorização corretos nossa requisição vai falhar.

Confira a listagem do método AssinarRequisicao:

Listagem3_thumb2

O primeiro elemento da assinatura é o método HTTP a ser utilizado. o Segundo elemento define o hash MD5 para a verificação da integridade, é opcional e não será utilizado neste exemplo. Adicionamos o Content-Type da requisição. O próximo elemento é a Data, desde que este elemento tenha sido definido no cabeçalho podemos passar uma string vazia. Classifica e ordena os cabeçalhos que se iniciam com x-ms. Com a sequência pronta, vamos utilizar nossa secret key para gerar um hash HMAC SHA256 e adicionar a autorização no cabeçalho.

Confira a listagem do método AssinarRequisicaoParaTable:

Listagem4_thumb2

Para se acessar o serviço de armazenamento de tabelas do azure foi necessário um pouco mais de trabalho da minha parte. O fato de trabalhar através de ADO.NET Data Services requer algumas especificações em relação aos demais serviços.

Observe que, para a assinatura de armazenamento da tabela, estou removendo a string de consulta a partir do recurso, mas para armazenamento de blobs e queues não há esta necessidade. Isso está documentado na API embora eu não tenha notado e isto tenha me valido um bom tempo.

Qual a real importância de se usar essas chaves? Cada pedido que você faz para o serviço de armazenamento tem uma URL e cabeçalhos que são incluídos com o pedido. Você usa a chave para assinar o pedido, e inseri a assinatura no pedido como um cabeçalho. Mesmo que o pedido seja interceptado, não será possível recuperar a sua chave privada a partir da solicitação. Como a data e a hora é parte do pedido, caso ele seja interceptado não será possível usá-lo para fazer novos pedidos.

No próximo post vamos falar sobre a codificação dos serviços de Blob, Queues, Tables e definições de conta.

Windows Azure Internals: Trabalhando com Storage Service e API REST (parte 1)

 

Um ótimo estudo a todos….

Ass copy

Twitter: @vitormeriat

vitormeriat@gmail.com

vitor.pereira@studentpartners.com.br


Author's profile picture

Vitor is a computer scientist who is passionate about creating software that will positively change the world we live in.

MVP Azure - Cloud Architect - Data science enthusiast


8 minutes to read