Exercício – Executar os testes de interface do usuário localmente e no pipeline

Concluído

Antes do Paulo e da Marina executarem os testes no pipeline, é necessário verificar se os novos testes de interface do usuário estão fazendo o que deveriam. Nesta seção, você acompanhará executando os testes de interface do usuário do Selenium primeiro localmente e, em seguida, no pipeline.

Escrever testes automatizados é um processo iterativo, assim como escrever qualquer outro tipo de código. Nos seus aplicativos, provavelmente você precisará tentar algumas abordagens, consultar a documentação de referência e o código de exemplo e consertar os erros de build.

Opcional: instale o driver do Selenium para Microsoft Edge

Siga esta seção se desejar ver os testes executados localmente no Microsoft Edge.

O pacote NuGet para Chrome e Firefox instala o software de driver no diretório bin, junto com o código de teste compilado. No Edge, você precisa instalar manualmente o driver. Para fazer isso:

  1. Instale o Microsoft Edge.

  2. Abra o Microsoft Edge e navegue para edge://settings/help. Observe o número de versão. Veja um exemplo:

    Uma captura de tela da página de configuração do Microsoft Edge mostrando o número de versão.

  3. Navegue até a página Downloads do driver do Microsoft Edge e baixe o driver que corresponde ao número de versão do Edge. Veja um exemplo:

    Captura de tela da seção Downloads da página Microsoft Edge Driver mostrando a versão do driver correspondente.

  4. Extraia o arquivo .zip no diretório bin/Release/net6.0 do diretório Tailspin.SpaceGame.Web.UITests do projeto. Crie esses diretórios se eles não existirem.

No macOS, talvez seja necessário atualizar a política do sistema para permitir que o msedgedriver seja executado. Para fazer isso, no Visual Studio Code, execute o seguinte comando spctl no terminal:

spctl --add Tailspin.SpaceGame.Web.UITests/bin/Release/net6.0/msedgedriver

Exportar variáveis de ambiente

Posteriormente neste módulo, você executará testes do Selenium no Windows Server 2019. A documentação lista o software pré-instalado para você.

A seção Drivers da Web do Selenium lista as versões do driver do Selenium que estão disponíveis para Chrome, Firefox e Edge. Veja um exemplo:

Uma captura de tela mostrando a documentação dos drivers do Selenium instalados no agente de build.

Em cada driver, você tem a variável de ambiente que é mapeada para a localização do driver. Por exemplo, o ChromeWebDriver é mapeado para a localização do driver do Chrome.

O código de testes de unidade já está configurado para ler essas variáveis de ambiente. Essas variáveis informam ao Selenium onde encontrar os arquivos executáveis do driver. Para executar os testes de unidade localmente, você precisa exportar essas mesmas variáveis de ambiente.

No Visual Studio Code, acesse o terminal. Em seguida, execute estes comandos. Substitua o caminho mostrado pelo caminho completo para o seu projeto mslearn-tailspin-spacegame-web-deploy.

Importante

Execute esses comandos e defina as variáveis de ambiente na mesma janela de terminal que você usa para executar os testes.

driverDir="C:\Users\user\mslearn-tailspin-spacegame-web-deploy\Tailspin.SpaceGame.Web.UITests\bin\Release\net6.0"
export ChromeWebDriver=$driverDir
export EdgeWebDriver=$driverDir
export GeckoWebDriver=$driverDir

Executar os testes da interface do usuário localmente

O método Setup em HomePageTest.cs navega para a home page do Space Game após definir a variável do membro driver.

Embora você possa embutir em código a URL do site, leia aqui a URL de uma variável de ambiente chamada SITE_URL. Dessa forma, você pode executar os testes várias vezes em diferentes URLs.

// Navigate to the site.
// The site name is stored in the SITE_URL environment variable to make 
// the tests more flexible.
string url = Environment.GetEnvironmentVariable("SITE_URL");
driver.Navigate().GoToUrl(url + "/");

Como você ainda não implantou o site do Space Game no seu ambiente do Serviço de Aplicativo, você usará o site que a Microsoft hospeda para executar os testes localmente.

Para executar os testes localmente:

  1. No Visual Studio Code, vá para o terminal integrado e abra uma nova janela de terminal.

  2. Execute os comandos a seguir na nova janela do terminal.

    dotnet build --configuration Release
    dotnet run --configuration Release --no-build --project Tailspin.SpaceGame.Web
    
  3. Anote o link do site local, neste exemplo, é http://localhost:5000.

  4. Volte para a janela do terminal em que você definiu as variáveis de ambiente na etapa anterior e verifique se você está no diretório raiz do projeto. Veja um exemplo:

    cd ~/mslearn-tailspin-spacegame-web-deploy
    
  5. Exporte a variável de ambiente SITE_URL. Use o link de execução local que você obteve da etapa anterior.

    export SITE_URL="http://localhost:5000"
    

    Essa variável aponta para o site do Space Game que a Microsoft hospeda.

  6. Execute os testes de interface do usuário.

    dotnet test --configuration Release Tailspin.SpaceGame.Web.UITests
    

    Esse código executa os testes que estão localizados no projeto Tailspin.SpaceGame.Web.UITests.

    Conforme os testes são executados, um ou mais navegadores são exibidos. O Selenium controla cada navegador e segue as etapas de teste que você definiu.

    Observação

    Não se preocupe se todos os três navegadores não aparecerem. Por exemplo, você não verá os testes executados no Chrome se não tiver o Chrome instalado ou se tiver uma versão incompatível. Ver apenas um navegador dará a você a confiança de que os seus testes estão funcionando. Na prática, no seu ambiente de desenvolvimento local, talvez você queira configurar todos os navegadores nos quais deseje testar. Essa configuração permitirá que você verifique se os testes se comportam conforme o esperado em cada configuração antes de executar os testes no pipeline.

  7. No terminal, rastreie a saída de cada teste. Observe também o resumo de execução de teste no final.

    Este exemplo mostra que, de nove testes, todos foram bem-sucedidos e nenhum foi ignorado:

    Passed!  - Failed:     0, Passed:     9, Skipped:     0, Total:     9, Duration: 5 s 
    

Adicionar a variável SITE_URL ao Azure Pipelines

Anteriormente, você definiu a variável de ambiente SITE_URL localmente para que os seus testes saibam quando apontar para cada navegador. Você pode adicionar essa variável ao Azure Pipelines. O processo é semelhante ao modo como você adicionou variáveis das suas instâncias do Serviço de Aplicativo. Quando o agente for executado, essa variável será exportada automaticamente para o agente como uma variável de ambiente.

Vamos adicionar a variável de pipeline agora, antes de atualizar a sua configuração de pipeline. Para fazer isso:

  1. No Azure DevOps, acesse o seu projeto Space Game – Web – Testes funcionais.

  2. Em Pipelines, selecione Library.

  3. Selecione o grupo de variáveis Release.

  4. Em Variables, selecione + Add.

  5. No nome da variável, insira SITE_URL. Como seu valor, insira a URL da instância do Serviço de Aplicativo que corresponde ao seu ambiente de teste, como http://tailspin-space-game-web-test-10529.azurewebsites.net.

  6. Próximo à parte superior da página, selecione Save para salvar a sua variável no pipeline.

    Seu grupo de variáveis deve ser semelhante a este:

    Captura de tela do Azure Pipelines mostrando o grupo de variáveis. O grupo contém quatro variáveis.

Modificar a configuração do pipeline

Nesta seção, você modificará a configuração de pipeline para executar os testes de interface do usuário do Selenium durante a fase de Teste.

  1. No Visual Studio Code, abra o arquivo azure-pipelines.yml. Em seguida, modifique o arquivo desta forma:

    Dica

    Esse arquivo contém algumas alterações, portanto, recomendamos que você substitua o arquivo inteiro pelo que você vê aqui.

    trigger:
    - '*'
    
    variables:
      buildConfiguration: 'Release'
      dotnetSdkVersion: '6.x'
    
    stages:
    - stage: 'Build'
      displayName: 'Build the web application'
      jobs: 
      - job: 'Build'
        displayName: 'Build job'
        pool:
          vmImage: 'ubuntu-20.04'
          demands:
          - npm
    
        variables:
          wwwrootDir: 'Tailspin.SpaceGame.Web/wwwroot'
          dotnetSdkVersion: '6.x'
    
        steps:
        - task: UseDotNet@2
          displayName: 'Use .NET SDK $(dotnetSdkVersion)'
          inputs:
            version: '$(dotnetSdkVersion)'
    
        - task: Npm@1
          displayName: 'Run npm install'
          inputs:
            verbose: false
    
        - script: './node_modules/.bin/node-sass $(wwwrootDir) --output $(wwwrootDir)'
          displayName: 'Compile Sass assets'
    
        - task: gulp@1
          displayName: 'Run gulp tasks'
    
        - script: 'echo "$(Build.DefinitionName), $(Build.BuildId), $(Build.BuildNumber)" > buildinfo.txt'
          displayName: 'Write build info'
          workingDirectory: $(wwwrootDir)
    
        - task: DotNetCoreCLI@2
          displayName: 'Restore project dependencies'
          inputs:
            command: 'restore'
            projects: '**/*.csproj'
    
        - task: DotNetCoreCLI@2
          displayName: 'Build the project - $(buildConfiguration)'
          inputs:
            command: 'build'
            arguments: '--no-restore --configuration $(buildConfiguration)'
            projects: '**/*.csproj'
    
        - task: DotNetCoreCLI@2
          displayName: 'Publish the project - $(buildConfiguration)'
          inputs:
            command: 'publish'
            projects: '$(System.DefaultWorkingDirectory)/**/Tailspin.SpaceGame.Web.csproj' 
            publishWebProjects: false
            arguments: '--no-build --configuration $(buildConfiguration) --output $(Build.ArtifactStagingDirectory)/$(buildConfiguration)'
            zipAfterPublish: true
    
        - publish: '$(Build.ArtifactStagingDirectory)'
          artifact: drop
    
    - stage: 'Dev'
      displayName: 'Deploy to the dev environment'
      dependsOn: Build
      jobs:
      - deployment: Deploy
        pool:
          vmImage: 'ubuntu-20.04'
        environment: dev
        variables:
        - group: Release
        strategy:
          runOnce:
            deploy:
              steps:
              - download: current
                artifact: drop
              - task: AzureWebApp@1
                displayName: 'Azure App Service Deploy: website'
                inputs:
                  azureSubscription: 'Resource Manager - Tailspin - Space Game'
                  appName: '$(WebAppNameDev)'
                  package: '$(Pipeline.Workspace)/drop/$(buildConfiguration)/*.zip'
    
    - stage: 'Test'
      displayName: 'Deploy to the test environment'
      dependsOn: Dev
      jobs:
      - deployment: Deploy
        pool:
          vmImage: 'ubuntu-20.04'
        environment: test
        variables:
        - group: 'Release'
        strategy:
          runOnce:
            deploy:
              steps:
              - download: current
                artifact: drop
              - task: AzureWebApp@1
                displayName: 'Azure App Service Deploy: website'
                inputs:
                  azureSubscription: 'Resource Manager - Tailspin - Space Game'
                  appName: '$(WebAppNameTest)'
                  package: '$(Pipeline.Workspace)/drop/$(buildConfiguration)/*.zip'
      - job: RunUITests
        dependsOn: Deploy
        displayName: 'Run UI tests'
        pool:
          vmImage: 'windows-2019'
        variables:
        - group: 'Release'
        steps: 
        - task: UseDotNet@2
          displayName: 'Use .NET SDK $(dotnetSdkVersion)'
          inputs:
            version: '$(dotnetSdkVersion)'
        - task: DotNetCoreCLI@2
          displayName: 'Build the project - $(buildConfiguration)'
          inputs:
            command: 'build'
            arguments: '--configuration $(buildConfiguration)'
            projects: '$(System.DefaultWorkingDirectory)/**/*UITests.csproj'
        - task: DotNetCoreCLI@2
          displayName: 'Run unit tests - $(buildConfiguration)'
          inputs:
            command: 'test'
            arguments: '--no-build --configuration $(buildConfiguration)'
            publishTestResults: true
            projects: '$(System.DefaultWorkingDirectory)/**/*UITests.csproj'
    
    - stage: 'Staging'
      displayName: 'Deploy to the staging environment'
      dependsOn: Test
      jobs:
      - deployment: Deploy
        pool:
          vmImage: 'ubuntu-20.04'
        environment: staging
        variables:
        - group: 'Release'
        strategy:
          runOnce:
            deploy:
              steps:
              - download: current
                artifact: drop
              - task: AzureWebApp@1
                displayName: 'Azure App Service Deploy: website'
                inputs:
                  azureSubscription: 'Resource Manager - Tailspin - Space Game'
                  appName: '$(WebAppNameStaging)'
                  package: '$(Pipeline.Workspace)/drop/$(buildConfiguration)/*.zip'
    

    O arquivo inclui estas três alterações:

    • A variável dotnetSdkVersion é movida para a parte superior do arquivo para que várias fases possam acessá-la. Nesse caso, a fase de Build e de Teste exigem esta versão do .NET Core.

    • A fase de Build publica apenas o pacote do site do Space Game como o artefato de compilação. Anteriormente, você publicou artefatos como este:

      - task: DotNetCoreCLI@2
        displayName: 'Publish the project - $(buildConfiguration)'
        inputs:
          command: 'publish'
          projects: '**/*.csproj'
          publishWebProjects: false
          arguments: '--no-build --configuration $(buildConfiguration) --output $(Build.ArtifactStagingDirectory)/$(buildConfiguration)'
          zipAfterPublish: true
      

      Essa tarefa gera dois artefatos de compilação: o pacote de site do Space Game e os testes de interface do usuário compilados. Criamos os testes de interface do usuário durante a fase Build para garantir que eles serão compilados durante a fase teste, mas não precisamos publicar o código de teste compilado. Ele é criado novamente durante a fase de Teste quando os testes são executados.

    • A fase de Teste inclui um segundo trabalho que cria e executa os testes. Esse trabalho é semelhante ao que você usou no módulo Executar testes de qualidade em seu pipeline de build usando o Azure Pipelines. Nesse módulo, você executou testes NUnit que verificaram a funcionalidade de filtragem do placar de líderes.

      Lembre-se de que um trabalho de implantação é um tipo especial de trabalho que desempenha um papel importante nas fases de implantação. O segundo trabalho é um trabalho normal que executa os testes do Selenium em um agente do Windows Server 2019. Embora possamos usar um agente do Linux para criar o aplicativo, aqui usaremos um agente do Windows para executar os testes de interface do usuário. Usamos um agente do Windows porque a Marina executa testes manuais no Windows, que é o que a maioria dos clientes usa.

      O trabalho RunUITests depende do trabalho Deploy para garantir que os trabalhos sejam executados na ordem correta. Você implantará o site no Serviço de Aplicativo antes de executar os testes de interface do usuário. Se você não especificar essa dependência, os trabalhos nessa fase poderão ser executados em qualquer ordem ou em paralelo.

  2. No terminal integrado, adicione azure-pipelines.yml ao índice, faça commit das alterações e efetue push do branch para o GitHub.

    git add azure-pipelines.yml
    git commit -m "Run Selenium UI tests"
    git push origin selenium
    

Assista aos Azure Pipelines executarem os testes

Nesta etapa, você inspeciona a execução de pipeline. O pipeline executa os testes de interface do usuário do Selenium durante a fase de Teste.

  1. No Azure Pipelines, acesse o build e rastreie-o enquanto ele é executado.

    Durante o build, você verá os testes automatizados executados depois que o site for implantado.

    Captura de tela do Azure Pipelines mostrando os estágios em execução.

  2. Após a conclusão do build, acesse a página de resumo.

    Captura de tela do Azure Pipelines mostrando os estágios concluídos.

    Você nota que a implantação e os testes de interface do usuário foram concluídos com êxito.

  3. Próximo à parte superior da página, observe o resumo.

    Você observa que o artefato de compilação do site do Space Game é publicado como sempre. Observe também a seção Tests and coverage, que mostra que os testes do Selenium foram aprovados.

    Captura de tela do Azure Pipelines mostrando o resumo do teste.

  4. Selecione o resumo do teste para ver o relatório completo.

    O relatório mostra que todos os nove testes foram aprovados. Esses testes incluem três testes em três navegadores.

    Captura de tela do Azure Pipelines mostrando o relatório completo do teste.

    Se algum teste falhar, você receberá resultados detalhados da falha. Desse ponto em diante, você pode investigar a origem da falha, consertá-la localmente e enviar por push as alterações necessárias para fazer com que os testes sejam aprovados no pipeline.

Marina: Esta automação é divertida! Agora tenho testes de interface do usuário que posso executar no pipeline. Os testes realmente pouparão tempo a longo prazo. Também tenho um padrão a ser seguido para adicionar mais testes. E o melhor de tudo é que os testes da interface do usuário aumentam a nossa confiança na qualidade do código.

Paulo: Exatamente. Lembre-se de que os testes que você executa repetidamente de modo manual são bons candidatos à automação. Boa sorte ao adicionar mais. Se você não souber o que fazer ou precisar de um revisor de código, saberá onde me encontrar.