Testando APIs da Web com coleções de carteiro
1. Introdução
Para testar completamente uma API da web, precisamos de algum tipo de cliente da web para acessar os endpoints da API. Postman is a standalone tool that exercises web APIs by making HTTP requests from outside the service.
Ao usar o Postman, não precisamos escrever nenhum código de infraestrutura de cliente HTTP apenas para fins de teste. Em vez disso, criamos conjuntos de testes chamados coleções e deixamos o Postman interagir com nossa API.
Neste tutorial, veremos como criar uma coleção Postman que pode testar uma API REST.
2. Configuração
Antes de começarmos com nossa coleção, precisaremos configurar o ambiente.
2.1. Instalando o Postman
O Postman está disponível para Linux, Mac e Windows. A ferramenta pode ser baixada e instalada emPostman website.
Depois de descartar a tela inicial, podemos ver a interface do usuário:
2.2. Executando o servidor
Postman needs a live HTTP server to process its requests. Para este tutorial, usaremos um projeto de exemplo anterior,spring-boot-rest,, que está disponível emGitHub.
Como podemos supor pelo título,spring-boot-rest é um aplicativo Spring Boot. Construímos o aplicativo com a meta Maveninstall. Depois de construído, iniciamos o servidor com o objetivo Maven personalizadospring-boot:run.
Para verificar se o servidor está em execução, podemos acessar este URL em nosso navegador:
http://localhost:8082/spring-boot-rest/auth/foos
Este serviço usa um banco de dados na memória. Todos os registros são limpos quando o servidor está parado.
3. Criando uma coleção de carteiro
Uma coleção no Postman é uma série de solicitações HTTP. O Postman salva todos os aspectos das solicitações, incluindo cabeçalhos e corpos das mensagens. Portanto,we can run the requests in sequence as semi-automated tests.
Vamos começar criando uma nova coleção. Podemos clicar na seta suspensa no botãoNewe selecionarCollection:
Quando a caixa de diálogoCREATE A NEW COLLECTION aparecer, podemos nomear nossa coleção “foo API test“. Por fim, clicamos no botãoCreate para ver nossa nova coleção aparecer na lista à esquerda:
Depois que nossa coleção é criada, podemos passar o cursor sobre ela para revelar dois botões de menu. O botão de seta abre um painel pull-right que fornece acesso aCollection Runner. Por outro lado, o botão de reticências abre um menu suspenso que contém várias operações na coleção.
4. Adicionando uma Solicitação POST
4.1. Criação de um novo pedido
Agora que temos uma coleção vazia, vamos adicionar uma solicitação que acesse nossa API. Especificamente, vamos enviar uma mensagem POST para o URI/auth/foos. Para fazer isso,we open the ellipsis menu on our collection and select Add Request.
Quando a caixa de diálogoSAVE REQUEST aparecer, vamos fornecer um nome descritivo, como “add a foo”. Em seguida, clique no botãoSave to foo API test.
Depois que a solicitação é criada, podemos ver que nossa coleção indicaone request. No entanto, se nossa coleção não foi expandida, não podemos ver a solicitação ainda. Nesse caso, podemos clicar na coleção para expandi-la.
Agora, devemos ver a nova solicitação listada em nossa coleção. Podemos observar que a nova solicitação, por padrão, é um HTTP GET, que não é o que queremos. Vamos corrigir isso na próxima seção:
4.2. Editando a Solicitação
Para editar a solicitação, vamos clicar nela, carregando-a na guia do editor de solicitações:
Embora o editor de solicitações tenha inúmeras opções, precisamos apenas de algumas delas por enquanto.
Em primeiro lugar, vamos usar o menu suspenso para alterar o método de GET para POST.
Em segundo lugar, precisamos de um URL. À direita do menu suspenso do método, há uma caixa de texto para o URL da solicitação. Então, vamos inserir isso agora:
http://localhost:8082/spring-boot-rest/auth/foos
O último passo é fornecer um corpo da mensagem. Abaixo do endereço do URL, há uma linha de cabeçalhos de guias. Clicaremos no cabeçalho da guiaBody para acessar o editor de corpo.
Na guiaBody, logo acima da área de texto, há uma linha de botões de opção e uma lista suspensa. Eles controlam a formatação e o tipo de conteúdo da solicitação.
Our service accepts JSON data, so we select the raw radio button. In the dropdown to the right, we apply the JSON (application/json) content type.
Depois de definir a codificação e o tipo de conteúdo, adicionamos nosso conteúdo JSON à área de texto:
{
"name": "Transformers"
}
Finalmente, vamos ter certeza de salvar nossas alterações pressionandoCtrl-S ou clicando no botãoSave. O botãoSave está localizado à direita do botãoSend. Depois de salvar, podemos ver que a solicitação foi atualizada para POST na lista à esquerda:
5. Executando a solicitação
5.1. Executando uma única solicitação
To run a single request, we just click the Send button à direita do endereço URL. Assim que clicarmos emSend,, o painel de resposta será aberto abaixo do painel de solicitação. Pode ser necessário rolar para baixo para vê-lo:
Vamos examinar nossos resultados. Especificamente, na barra de cabeçalho, vemos que nossa solicitação foi bem-sucedida com o status201 Created. Além disso, o corpo da resposta mostra que nosso registroTransformers recebeu uma id de 1.
5.2. Usando o Runner de coleta
In contrast to the Send button, the collection runner can execute an entire collection. Para iniciar o corredor de coleta, passamos o cursor sobre nossa coleçãofoo API test e clicamos na seta para puxar para a direita. No painel puxado à direita, podemos ver um botãoRun, então vamos clicar nele:
Quando clicamos no botãoRun, o corredor de coleta é aberto em uma nova janela. Como o lançamos em nossa coleção, o corredor já foi inicializado em nossa coleção:
O executor de coleta oferece opções que afetam a execução do teste, mas não precisaremos delas para este exercício. Vamos diretamente ao botãoRun foo API test na parte inferior e clique nele.
Quando executamos a coleção, a visualização muda paraRun Results. Nesta visualização,we see a list of tests that are marked green for success and red for failure.
Embora nossa solicitação tenha sido enviada, o corredor indica que zero testes foram aprovados e zero falharam. Isso ocorre porque ainda não adicionamos testes à nossa solicitação:
6. Testando a Resposta
6.1. Adicionar testes a um pedido
Para criar um teste, vamos retornar ao painel de edição de solicitação onde construímos nosso método POST. Clicamos na guiaTests, localizada abaixo do URL. Quando fazemos isso, o painel Testes é exibido:
No painel Testes, escrevemos JavaScript que será executado quando a resposta for recebida do servidor.
Postman offers built-in variables that provide access to the request and response. Além disso, várias bibliotecas JavaScript podem ser importadas usando a sintaxerequire().
Existem muitos recursos de script a serem abordados neste tutorial. No entanto, oofficial Postman documentation é um excelente recurso neste tópico.
Vamos continuar adicionando três testes à nossa solicitação:
pm.test("success status", () => pm.response.to.be.success );
pm.test("name is correct", () =>
pm.expect(pm.response.json().name).to.equal("Transformers"));
pm.test("id was assigned", () =>
pm.expect(pm.response.json().id).to.be.not.null );
Como podemos ver,these tests make use of the global pm module provided by Postman. Em particular, os testes usampm.test(), pm.expect() epm.response.
A funçãopm.test() aceita um rótulo e uma função de asserção,, comoexpect(). Estamos usandopm.expect() para declarar condições sobre o conteúdo do JSON de resposta.
O objetopm.response fornece acesso a várias propriedades e operações na resposta retornada do servidor. As propriedades disponíveis incluem o status da resposta e o conteúdo JSON, entre outras.
Como sempre, salvamos nossas alterações comCtrl-S ou o botãoSave.
6.2. Executando os testes
Agora que temos nossos testes, vamos executar a solicitação novamente. Pressionar o botãoSend exibe os resultados na guiaTest Results do painel de resposta:
Da mesma forma, o corredor de coleta agora exibe nossos resultados de teste. Especificamente, o resumo no canto superior esquerdo mostra os totais atualizados depassedefailed. Abaixo do resumo, há uma lista que mostra cada teste com seu status:
6.3. Visualizando o Postman Console
OPostman Console é uma ferramenta útil para criar e depurar scripts. Podemos encontrar o console no menuView com o nome do itemShow Postman Console. Quando iniciado, o console é aberto em uma nova janela.
While the console is open, it records all HTTP requests and responses. Além disso, quando os scripts usamconsole.log(),, oPostman Console exibe essas mensagens:
7. Criação de uma sequência de solicitações
Até agora, nos concentramos em uma única solicitação HTTP. Agora, vamos ver o que podemos fazer com várias solicitações. By chaining together a series of requests, we can simulate and test a client-server workflow.
Nesta seção, vamos aplicar o que aprendemos para criar uma sequência de solicitações. Especificamente, adicionaremos mais três solicitações para executar após a solicitação POST que já criamos. Estes serão um GET, um DELETE e, finalmente, outro GET.
7.1. Capturando Valores de Resposta em Variáveis
Antes de criarmos nossas novas solicitações, vamos fazer uma modificação em nossa solicitação POST existente. Como não sabemos qual id o servidor irá atribuir a cada instânciafoo, podemos usar uma variável para capturar o id retornado pelo servidor.
Para capturar esse id, adicionaremos mais uma linha ao final do script de teste da solicitação POST:
pm.variables.set("id", pm.response.json().id);
The pm.variables.set() function takes a value and assigns it to a temporary variable. Neste caso, estamos criando uma variávelid para armazenar o valor de id do nosso objeto. Uma vez definido, podemos acessar essa variável em solicitações posteriores.
7.2. Adicionando uma solicitação GET
Agora, usando as técnicas das seções anteriores, vamos adicionar uma solicitação GET após a solicitação POST.
With this GET request, we’ll retrieve the same foo instance that the POST request created. Vamos nomear essa solicitação GET como “get a foo“.
O URL da solicitação GET é:
http://localhost:8082/spring-boot-rest/auth/foos/{{id}}
Neste URL, estamos nos referindo à variávelid que definimos anteriormente durante a solicitação POST. Portanto, a solicitação GET deve recuperar a mesma instância que foi criada pelo POST.
As variáveis, quando aparecem fora dos scripts, são referenciadas usando a sintaxe de chave dupla\{{id}}.
Como não há corpo para uma solicitação GET, vamos prosseguir diretamente para a guiaTests. Como os testes são semelhantes, podemos copiá-los da solicitação POST e, em seguida, fazer algumas alterações.
Em primeiro lugar,we don’t need to set the id variable again, então não vamos copiar essa linha.
Em segundo lugar, sabemos qual id esperar desta vez, então vamos verificar essa id. Podemos usar a variávelid para fazer isso:
pm.test("success status", () => pm.response.to.be.success );
pm.test("name is correct", () =>
pm.expect(pm.response.json().name).to.equal("Transformers"));
pm.test("id is correct", () =>
pm.expect(pm.response.json().id).to.equal(pm.variables.get("id")) );
Since the double-brace syntax is not valid JavaScript, we use the pm.variables.get() function to access the id variable.
Finalmente, vamos salvar as alterações como fizemos antes.
7.3. Adicionando uma solicitação DELETE
A seguir, adicionaremos uma solicitação DELETE que removerá o objetofoo do servidor.
Continuaremos adicionando uma nova solicitação após GET e definindo seu método como DELETE. Podemos nomear essa solicitação “delete a foo“.
O URL da exclusão é idêntico ao URL GET:
http://localhost:8082/spring-boot-rest/auth/foos/{{id}}
The response will not have a body to test, but we can test the response code. Portanto, a solicitação DELETE terá apenas um teste:
pm.test("success status", () => pm.response.to.be.success );
7.4. Verificando o DELETE
Finalmente, vamos adicionar outra cópia da solicitação GET para verificar se o DELETE realmente funcionou. Desta vez, vamos duplicar nossa primeira solicitação GET em vez de criar uma solicitação do zero.
Para duplicar uma solicitação, clique com o botão direito do mouse na solicitação para mostrar o menu suspenso. Então, selecionamosDuplicate.
A solicitação duplicada terá a palavraCopy anexada ao seu nome. Vamos renomear para "verify delete" para evitar confusão. A opçãoRename está disponível clicando com o botão direito na solicitação.
Por padrão, a solicitação duplicada aparece imediatamente após a solicitação original. Como resultado, precisaremos arrastá-lo para baixo da solicitação DELETE.
O passo final é modificar os testes. No entanto, antes de fazermos isso, vamos aproveitar a oportunidade para ver um teste que falhou.
Copiamos a solicitação GET e movemos após DELETE, mas ainda não atualizamos os testes. Como a solicitação DELETE deveria ter excluído o objeto, os testes deverão falhar.
Certifique-se de salvar todas as nossas solicitações e, em seguida, pressioneRetry no runner de coleta. Como esperado, nossos testes falharam:
Agora que nosso breve desvio foi concluído, vamos corrigir os testes.
Ao revisar os testes com falha, podemos ver que o servidor responde com um status 500. Portanto, vamos mudar o status em nosso teste.
Além disso, ao visualizar a resposta com falha emPostman Console, descobrimos que a resposta inclui uma propriedadecause. Além disso, a propriedadecause contém a string “No value present“. Também podemos testar isso:
pm.test("status is 500", () => pm.response.to.have.status(500) );
pm.test("no value present", () =>
pm.expect(pm.response.json().cause).to.equal("No value present"));
8. Exportando e importando a coleção
While Postman stores our collections in a private, local location, we may want to share the collection. To do that, we export the collection to a JSON file.
O comandoExport está disponível no menu de reticências da coleção. Quando for solicitada uma versão do arquivo JSON, vamos escolher a versão mais recente recomendada.
Depois de selecionar a versão do arquivo, o Postman solicitará um nome de arquivo e um local para a coleção exportada. Podemos escolher uma pasta dentro do nosso projeto GitHub, por exemplo.
To import a previously exported collection, we use the Import button. Podemos encontrá-lo na barra de ferramentas da janela principal do Postman. Quando o Postman solicita um local para o arquivo, podemos navegar para o arquivo JSON que desejamos importar.
É importante notar que o Postman não rastreia arquivos exportados. Como resultado, o Postman não mostra alterações externas até que importemos novamente a coleção.
9. Conclusão
Neste artigo, usamos o Postman para criar testes semi-automatizados para uma API REST. Embora este artigo sirva como uma introdução aos recursos básicos do Postman, mal tocamos a superfície de seus recursos. OPostman online documentation é um recurso valioso para uma exploração mais profunda.
A coleção criada neste tutorial está disponível emGitHub.