portaldacalheta.pt
  • Principal
  • Ferramentas E Tutoriais
  • Noticias Do Mundo
  • Pessoas E Equipes
  • Ascensão Do Remoto
Tecnologia

Teste de solicitação HTTP: uma ferramenta de sobrevivência do desenvolvedor



O que fazer quando um conjunto de testes não for viável

Há momentos em que nós - programadores e / ou nossos clientes - temos recursos limitados com os quais escrever a entrega esperada e os testes automatizados para essa entrega. Quando o aplicativo é pequeno o suficiente, você pode cortar atalhos e pular testes porque você se lembra (principalmente) do que acontece em outras partes do código quando você adiciona um recurso, corrige um bug ou refatora. Dito isso, nem sempre trabalharemos com aplicativos pequenos, além disso, eles tendem a ficar maiores e mais complexos com o tempo. Isso torna o teste manual difícil e muito chato.

Nos meus últimos projetos, fui forçado a trabalhar sem testes automatizados e, honestamente, foi constrangedor ter o cliente me enviando um e-mail após um push de código para dizer que o aplicativo estava quebrando em lugares onde eu nem tinha tocado no código.



Portanto, nos casos em que meu cliente não tinha orçamento ou intenção de adicionar qualquer estrutura de teste automatizado, comecei a testar a funcionalidade básica de todo o site enviando uma solicitação HTTP para cada página individual, analisando os cabeçalhos de resposta e procurando o '200' resposta. Parece claro e simples, mas há muito que você pode fazer para garantir a fidelidade sem realmente ter que escrever nenhum teste, unidade, funcional ou integração.



Teste Automatizado

No desenvolvimento web, os testes automatizados são compostos por três tipos principais de teste: testes de unidade, testes funcionais e testes de integração. Freqüentemente, combinamos testes de unidade com testes funcionais e de integração para garantir que tudo funcione perfeitamente como um aplicativo completo. Quando esses testes são executados em uníssono, ou sequencialmente (de preferência com um único comando ou clique), passamos a chamá-los de testes automatizados, unitários ou não.



Em grande parte, o objetivo desses testes (pelo menos em desenvolvimento web) é garantir que todas as páginas do aplicativo sejam renderizadas sem problemas, livres de erros fatais (interrupção do aplicativo) ou bugs.

gerador de site estático node js

Teste de Unidade

O teste de unidade é um processo de desenvolvimento de software no qual as menores partes do código - unidades - são testadas de forma independente para operação correta. Aqui está um exemplo em Ruby:



test “should return active users” do active_user = create(:user, active: true) non_active_user = create(:user, active: false) result = User.active assert_equal result, [active_user] end

Teste funcional

O teste funcional é uma técnica usada para verificar os recursos e a funcionalidade do sistema ou software, projetado para cobrir todos os cenários de interação do usuário, incluindo caminhos de falha e casos de limite.

Nota: todos os nossos exemplos estão em Ruby.



test 'should get index' do get :index assert_response :success assert_not_nil assigns(:object) end

Teste de integração

Uma vez que os módulos são testados por unidade, eles são integrados um a um, sequencialmente, para verificar o comportamento combinacional e para validar se os requisitos foram implementados corretamente.

test 'login and browse site' do # login via https https! get '/login' assert_response :success post_via_redirect '/login', username: users(:david).username, password: users(:david).password assert_equal '/welcome', path assert_equal 'Welcome david!', flash[:notice] https!(false) get '/articles/all' assert_response :success assert assigns(:articles) end

Testes em um mundo ideal

O teste é amplamente aceito na indústria e faz sentido; bons testes permitem que você:



  • A qualidade garante toda a sua aplicação com o mínimo esforço humano
  • Identifique os bugs com mais facilidade porque você sabe exatamente onde seu código está quebrando com as falhas de teste
  • Crie documentação automática para o seu código
  • Evitar ‘Codificação da constipação’ , o que, de acordo com um cara do Stack Overflow, é uma maneira bem-humorada de dizer: 'quando você não souber o que escrever a seguir, ou tiver uma tarefa difícil pela frente, comece escrevendo pequeno'.

Eu poderia ficar falando sem parar sobre como os testes são incríveis e como eles mudaram o mundo e blá blá blá, mas você entendeu. Conceitualmente, os testes são fantásticos.

Relacionado: Testes de unidade, como escrever código testável e por que é importante

Testes no mundo real

Embora haja méritos em todos os três tipos de teste, eles não são escritos na maioria dos projetos. Por quê? Bem, deixe-me decifrar:



Tempo / Prazos

Todo mundo tem prazos, e escrever novos testes pode atrapalhar o cumprimento de um. Pode levar tempo e meio (ou mais) para escrever um aplicativo e seus respectivos testes. Agora, alguns de vocês não concordam com isso, citando o tempo economizado em última análise, mas não acho que seja esse o caso e explicarei o porquê em ‘Diferença de opinião’.

Problemas do cliente

Frequentemente, o cliente não entende realmente o que é teste ou por que ele tem valor para o aplicativo. Os clientes tendem a se preocupar mais com a entrega rápida do produto e, portanto, consideram os testes programáticos contraproducentes.



Ou pode ser tão simples quanto o cliente não ter orçamento para pagar pelo tempo extra necessário para implementar esses testes.

Falta de conhecimento

Existe uma tribo considerável de desenvolvedores no mundo real que não sabe que existe o teste. Em cada conferência, encontro, show, (mesmo em meus sonhos), encontro desenvolvedores que não sabem escrever testes, não sabem o que testar, não sabem como configurar a estrutura para testes, e assim em. O teste não é exatamente ensinado nas escolas e pode ser um incômodo configurar / aprender a estrutura para colocá-los em funcionamento. Então, sim, há uma barreira definitiva para a entrada.

'É um monte de trabalho'

Escrever testes pode ser opressor para programadores novos e experientes, mesmo para os tipos de gênios que mudam o mundo, e ainda por cima, escrever testes não é emocionante. Alguém pode pensar: “Por que eu deveria me envolver em uma ocupação pouco excitante quando poderia implementar um recurso importante com resultados que impressionarão meu cliente?” É um argumento difícil.

Por último, mas não menos importante, é difícil escrever testes e os alunos de ciência da computação não são treinados para isso.

Ah, e refatorar com testes de unidade não é divertido.

Diferença de opinião

Em minha opinião, o teste de unidade faz sentido para lógica algorítmica, mas não tanto para coordenar código vivo.

um bom design de banco de dados não inclui:

As pessoas afirmam que, embora você esteja investindo tempo extra antecipadamente na escrita de testes, você economiza horas depois ao depurar ou alterar o código. Eu discordo e ofereço uma pergunta: seu código está estático ou está sempre mudando?

Para a maioria de nós, está sempre mudando. Se você está escrevendo um software de sucesso, está sempre adicionando recursos, alterando os existentes, removendo-os, comendo-os, o que for, e para acomodar essas alterações, você deve continuar alterando seus testes, e mudar seus testes leva tempo.

Mas, você precisa de algum tipo de teste

Ninguém vai argumentar que a falta de qualquer tipo de teste é o pior caso possível. Depois de fazer alterações em seu código, você precisa confirmar se ele realmente funciona. Muitos programadores tentam testar manualmente o básico: a página é renderizada no navegador? O formulário está sendo enviado? O conteúdo correto está sendo exibido? E assim por diante, mas na minha opinião, isso é bárbaro, ineficiente e trabalhoso.

O que eu uso no lugar

O objetivo de testar um aplicativo da web, seja manualmente ou automatizado, é confirmar se qualquer página é renderizada no navegador do usuário sem erros fatais e que mostra seu conteúdo corretamente. Uma maneira (e na maioria dos casos, uma maneira mais fácil) de fazer isso é enviar solicitações HTTP aos endpoints do aplicativo e analisar a resposta. O código de resposta informa se a página foi entregue com sucesso. É fácil testar o conteúdo analisando o corpo da resposta da solicitação HTTP e procurando por correspondências de string de texto específicas ou, você pode ser um passo mais avançado e usar bibliotecas de scraping da web, como Nokogiri .

Se alguns endpoints exigem um login de usuário, você pode usar bibliotecas projetadas para automatizar interações (ideal ao fazer testes de integração), como mecanizar para fazer o login ou clicar em determinados links. Na verdade, no quadro geral dos testes automatizados, isso se parece muito com integração ou teste funcional (dependendo de como você os usa), mas é muito mais rápido de escrever e pode ser incluído em um projeto existente ou adicionado a um novo , com menos esforço do que configurar toda a estrutura de teste. Spot on!

Relacionado: Contrate os melhores 3% dos engenheiros autônomos de controle de qualidade.

Os casos extremos apresentam outro problema ao lidar com grandes bancos de dados com uma ampla gama de valores; testar se nosso aplicativo está funcionando sem problemas em todos os conjuntos de dados antecipados pode ser assustador.

Uma maneira de fazer isso é antecipar todos os casos extremos (o que não é apenas difícil, mas muitas vezes impossível) e escrever um teste para cada um. Isso poderia facilmente se tornar centenas de linhas de código (imagine o horror) e difícil de manter. Ainda assim, com solicitações HTTP e apenas uma linha de código, você pode testar esses casos extremos diretamente nos dados de produção, baixados localmente em sua máquina de desenvolvimento ou em um servidor de teste.

É claro que essa técnica de teste não é uma solução mágica e tem muitas falhas, como qualquer outro método, mas acho esses tipos de testes mais rápidos e fáceis de escrever e modificar.

Na prática: teste com solicitações HTTP

Como já estabelecemos que escrever código sem nenhum tipo de teste de acompanhamento não é uma boa ideia, meu teste básico para um aplicativo inteiro é enviar solicitações HTTP para todas as suas páginas localmente e analisar os cabeçalhos de resposta para um 200 código (ou desejado).

Por exemplo, se fossemos escrever os testes acima (aqueles que procuram por conteúdo específico e um erro fatal) com uma solicitação HTTP (em Ruby), seria algo assim:

por que o desenvolvimento do Android é tão complicado
# testing for fatal error http_code = `curl -X #{route[:method]} -s -o /dev/null -w '%{http_code}' #{Rails.application.routes.url_helpers.articles_url(host: 'localhost', port: 3000) }` if http_code !~ /200/ return “articles_url returned with #{http_code} http code.” end # testing for content active_user = create(:user, name: “user1”, active: true) non_active_user = create(:user, name: “user2”, active: false) content = `curl #{Rails.application.routes.url_helpers.active_user_url(host: 'localhost', port: 3000) }` if content !~ /#{active_user.name}/ return “Content mismatch active user #{active_user.name} not found in text body” #You can customise message to your liking end if content =~ /#{non_active_user.name}/ return “Content mismatch non active user #{active_user.name} found in text body” #You can customise message to your liking end

A linha curl -X #{route[:method]} -s -o /dev/null -w '%{http_code}' #{Rails.application.routes.url_helpers.articles_url(host: 'localhost', port: 3000) } cobre muitos casos de teste; qualquer método que gerar um erro na página do artigo será detectado aqui, portanto, cobre efetivamente centenas de linhas de código em um teste.

A segunda parte, que detecta especificamente o erro de conteúdo, pode ser usada várias vezes para verificar o conteúdo de uma página. (Solicitações mais complexas podem ser tratadas usando mechanize, mas isso está além do escopo deste blog.)

Agora, nos casos em que você deseja testar se uma página específica funciona em um conjunto grande e variado de valores de banco de dados (por exemplo, seu modelo de página de artigo está funcionando para todos os artigos no banco de dados de produção), você pode fazer:

ids = Article.all.select { |post| `curl -s -o /dev/null -w “%{http_code}” #{Rails.application.routes.url_helpers.article_url(post, host: 'localhost', port: 3000) }`.to_i != 200).map(&:id) return ids

Isso retornará uma matriz de IDs de todos os artigos no banco de dados que não foram renderizados, então agora você pode ir manualmente para a página do artigo específico e verificar o problema.

Agora, eu entendo que esta forma de teste pode não funcionar em certos casos, como testar um script autônomo ou enviar um e-mail, e é inegavelmente mais lento do que os testes de unidade porque estamos fazendo chamadas diretas para um endpoint para cada teste, mas quando você não pode ter testes de unidade, ou testes funcionais, ou ambos, isso é melhor do que nada.

em qual linguagem os x está escrito

Como você faria para estruturar esses testes? Com projetos pequenos e não complexos, você pode escrever todos os seus testes em um arquivo e executar esse arquivo todas as vezes antes de confirmar suas alterações, mas a maioria dos projetos exigirá um conjunto de testes.

Normalmente escrevo de dois a três testes por endpoint, dependendo do que estou testando. Você também pode tentar testar o conteúdo individual (semelhante ao teste de unidade), mas acho que seria redundante e lento, pois você fará uma chamada HTTP para cada unidade. Mas, por outro lado, eles serão mais limpos e fáceis de entender.

Eu recomendo colocar seus testes em sua pasta de teste regular com cada endpoint principal tendo seu próprio arquivo (em Rails, por exemplo, cada modelo / controlador teria um arquivo cada), e este arquivo pode ser dividido em três partes de acordo com o que nós estão testando. Costumo fazer pelo menos três testes:

Teste Um

Verifique se a página retorna sem erros fatais.

O teste um verifica se a página retorna sem erros fatais.

Observe como fiz uma lista de todos os pontos de extremidade para Post e iterado sobre ele para verificar se cada página é renderizada sem nenhum erro. Supondo que tudo tenha corrido bem e todas as páginas renderizadas, você verá algo assim no terminal: ➜ sample_app git:(master) ✗ ruby test/http_request/post_test.rb List of failed url(s) -- []

Se alguma página não for renderizada, você verá algo assim (neste exemplo, o posts/index page tem erro e, portanto, não é renderizado): ➜ sample_app git:(master) ✗ ruby test/http_request/post_test.rb List of failed url(s) -- [{:url=>”posts_url”, :params=>[], :method=>”GET”, :http_code=>”500”}]

Teste Dois

Confirme se todo o conteúdo esperado está lá:

exemplo de programação linear inteira mista

O teste dois confirma que todo o conteúdo esperado está lá.

Se todo o conteúdo que esperamos for encontrado na página, o resultado será semelhante a este (neste exemplo, certificamo-nos de que posts/:id tem um título de postagem, uma descrição e um status): ➜ sample_app git:(master) ✗ ruby test/http_request/post_test.rb List of content(s) not found on Post#show page with post id: 1 -- []

Se algum conteúdo esperado não for encontrado na página (aqui esperamos que a página mostre o status da postagem - 'Ativo' se a postagem estiver ativa, 'Desativado' se a postagem estiver desabilitada), o resultado será assim: ➜ sample_app git:(master) ✗ ruby test/http_request/post_test.rb List of content(s) not found on Post#show page with post id: 1 -- [“Active”]

Teste Três

Verifique se a página é renderizada em todos os conjuntos de dados (se houver):

O teste 3 verifica se a página é renderizada em todos os conjuntos de dados.

Se todas as páginas forem renderizadas sem nenhum erro, obteremos uma lista vazia: ➜ sample_app git:(master) ✗ ruby test/http_request/post_test.rb List of post(s) with error in rendering -- []

Se o conteúdo de alguns dos registros apresentar um problema de renderização (neste exemplo, as páginas com ID 2 e 5 apresentam um erro), o resultado será o seguinte: ➜ sample_app git:(master) ✗ ruby test/http_request/post_test.rb List of post(s) with error on rendering -- [2,5]

Se você quiser mexer no código de demonstração acima, aqui está o meu projeto github .

Então, qual é melhor? Depende…

O teste de solicitação HTTP pode ser sua melhor aposta se:

  • Você está trabalhando com um aplicativo da web
  • Você está com o tempo apertado e quer escrever algo rápido
  • Você está trabalhando com um grande projeto, um projeto pré-existente onde os testes não foram escritos, mas ainda quer alguma maneira de verificar o código
  • Seu código envolve solicitação e resposta simples
  • Você não quer gastar uma grande parte do seu tempo mantendo testes (eu li em algum lugar teste de unidade = inferno de manutenção, e concordo parcialmente com ele)
  • Você quer testar se um aplicativo funciona em todos os valores em um banco de dados existente

O teste tradicional é ideal quando:

  • Você está lidando com algo diferente de um aplicativo da web, como scripts
  • Você está escrevendo um código complexo de algoritmos
  • Você tem tempo e orçamento para dedicar à redação de testes
  • O negócio requer um livre de bugs ou uma taxa de erro baixa (finanças, grande base de usuários)

Obrigado por ler o artigo; Agora você deve ter um método de teste que pode ser padronizado, um método com o qual pode contar quando estiver sem tempo.

Relacionado:
  • Desempenho e eficiência: trabalhando com HTTP / 3
  • Mantenha-o criptografado, mantenha-o seguro: trabalhando com ESNI, DoH e DoT

Hospedando uma Conferência Técnica para uma Rede de Desenvolvedores de Software: O Evento CordobaJS

Estilo De Vida

Hospedando uma Conferência Técnica para uma Rede de Desenvolvedores de Software: O Evento CordobaJS
Seleção dos melhores blogs de desenvolvedores da ApeeScape

Seleção dos melhores blogs de desenvolvedores da ApeeScape

Tecnologia

Publicações Populares
Manter frameworks PHP MVC Slim com uma estrutura em camadas
Manter frameworks PHP MVC Slim com uma estrutura em camadas
Modelos de preços SaaS - exemplos de estratégia de preços e práticas recomendadas
Modelos de preços SaaS - exemplos de estratégia de preços e práticas recomendadas
A pessoa mais velha do mundo, a italiana Emma Morano, morre aos 117 anos
A pessoa mais velha do mundo, a italiana Emma Morano, morre aos 117 anos
Salesforce Einstein AI: um tutorial de API
Salesforce Einstein AI: um tutorial de API
UX em evolução - Design de produto experimental com um CXO
UX em evolução - Design de produto experimental com um CXO
 
Na adolescência, o estresse excessivo pode desencadear acidez
Na adolescência, o estresse excessivo pode desencadear acidez
Princípios de Design Organizacional e Otimização: Lições da Grande Recessão
Princípios de Design Organizacional e Otimização: Lições da Grande Recessão
Da política à família: como a indicação de Kamala Harris é relevante para a Índia
Da política à família: como a indicação de Kamala Harris é relevante para a Índia
Implementando um servidor Framebuffer remoto em Java
Implementando um servidor Framebuffer remoto em Java
Republicanos e democratas criticam Trump por reivindicar a vitória prematuramente
Republicanos e democratas criticam Trump por reivindicar a vitória prematuramente
Publicações Populares
  • o que é uma corporação llc s
  • guia de estudo do arquiteto de soluções certificadas aws
  • s corp vs. c corp
  • artigos de Warren Buffett sobre Investimentos
  • c ++ aprender fazendo
  • s corporação vs c corp
  • o que é um discord bot
Categorias
  • Ferramentas E Tutoriais
  • Noticias Do Mundo
  • Pessoas E Equipes
  • Ascensão Do Remoto
  • © 2022 | Todos Os Direitos Reservados

    portaldacalheta.pt