Comandos do shell do dispositivo

Durante os testes de VTS, os comandos do shell são usados para executar um binário de teste do lado do destino, para receber/definir propriedades, variáveis de ambiente e informações do sistema e para iniciar/parar o framework do Android. É possível executar comandos do shell do dispositivo VTS usando o comando adb shell ou o driver do shell VTS em execução no dispositivo (recomendado).

Usar o shell do ADB

Os testes que exigem o desligamento da porta USB ou a reinicialização do dispositivo durante o teste precisam usar o shell do ADB, porque o driver do shell do VTS fica indisponível sem uma conexão USB persistente. É possível invocar o shell do ADB no objeto AndroidDevice no script de teste do Python. Exemplos:

  • Receber um objeto de dispositivo Android:
    self.device = self.android_devices[0]
    
  • Emita um único comando do shell:
    result = self.device.adb.shell(‘ls')
    

Usar o driver de shell VTS

O driver de shell do VTS é um agente binário que é executado no dispositivo e executa comandos de shell. Por padrão, o VTS usa o driver do shell se ele estiver em execução no dispositivo, porque esse método tem menos latência do que usar o comando adb shell.

Figura 1. Driver de shell do VTS.

O framework VTS oferece suporte a testes em vários dispositivos, em que cada dispositivo Android é representado como um objeto AndroidDevice no executor de base. Por padrão, o framework VTS envia binários do agente e do driver do shell do VTS para cada dispositivo Android e estabelece conexões TCP com os agentes do VTS nesses dispositivos.

Para executar um comando do shell, o script Python do host faz uma chamada de função para o objeto ShellMirror dentro do objeto AndroidDevice. O objeto ShellMirror empacota os textos de comando do shell em uma mensagem protobuf e a envia (pelo canal TCP) ao agente VTS no dispositivo Android. O agente em execução no dispositivo encaminha o comando do shell para o driver do shell VTS pelo soquete Unix.

Quando o driver de shell do VTS recebe um comando de shell, ele executa o comando por nohup no shell do dispositivo para evitar travamentos. O stdout, o stderr e o código de retorno são recuperados de nohup e enviados de volta ao agente VTS. Por fim, o agente responde ao host agrupando os resultados do comando em uma mensagem protobuf.

Vantagens

As vantagens de usar o driver de shell do VTS em vez de adb shell incluem:

  • Confiabilidade. O driver de shell do VTS usa nohup para executar comandos na configuração padrão. Como os testes do VTS são principalmente testes HAL e kernel de nível mais baixo, nohup garante que os comandos do shell não travem durante a execução.
  • Desempenho. Embora o comando adb shell armazene em cache alguns resultados (como a listagem de arquivos em um diretório), ele tem um overhead de conexão ao realizar tarefas, como a execução de um binário de teste. O driver de shell do VTS mantém uma conexão ativa durante o teste, portanto, o único overhead é a comunicação USB. Em nossos testes, o uso do driver de shell do VTS para executar um comando com 100 chamadas para um binário gtest vazio é cerca de 20% mais rápido do que o uso de adb shell. A diferença real é maior, já que a comunicação do shell do VTS tem um registro extenso.
  • Estado. O driver de shell do VTS mantém uma sessão de terminal para cada nome de terminal (o nome padrão é default). As variáveis de ambiente definidas em uma sessão de terminal estão disponíveis apenas para comandos subsequentes na mesma sessão.
  • Extensível. As comunicações de comando do shell entre o framework VTS e o driver do dispositivo são agrupadas em protobuf para permitir a possível compressão, acesso remoto, criptografia etc. no futuro. Outras possibilidades de melhoria de desempenho também estão disponíveis, incluindo a análise de resultados do dispositivo quando o overhead de comunicação se torna maior que a análise de strings de resultados.

Desvantagens

As desvantagens de usar o driver de shell do VTS em vez de adb shell incluem:

  • Binários adicionais. Os arquivos do agente do VTS precisam ser enviados para o dispositivo e limpos após a execução do teste.
  • Requer conexão ativa. Se a conexão TCP entre o host e o agente for perdida durante o teste (devido a desconexão USB, desligamento da porta, falha do dispositivo etc.), intencionalmente ou não, um comando de shell não poderá ser transmitido ao agente do VTS. Mesmo com a mudança automática para adb shell, o resultado e o estado do comando antes da desconexão seriam desconhecidos.

Exemplos

Exemplos de uso de comandos do shell em um script de teste Python do lado do host do VTS:

  • Receber um objeto de dispositivo Android:
    self.device = self.android_devices[0]
    
  • Receba um objeto de shell para o dispositivo selecionado:
    self.shell = self.device.shell
    
  • Emita um único comando do shell:
    results = self.shell.Execute(‘ls')
    
  • Emita uma lista de comandos do shell:
    results = self.shell.Execute([‘cd /data/local/tmp', ‘ls'])
    

Objeto de resultado de comando

O objeto de retorno da execução do comando do shell é um dicionário que contém as chaves stdouts, stderrs e return_codes. Independentemente de o comando do shell ser fornecido como uma única string ou uma lista de strings de comando, cada valor do dicionário de resultados é sempre uma lista.

Para verificar o código de retorno de uma lista de comandos, o script de teste precisa verificar os índices. Exemplo:

asserts.assertFalse(any(results[‘return_codes']), ‘some command failed.')

Como alternativa, o script pode verificar cada índice de comando individualmente. Exemplo:

asserts.assertEqual(results[‘return_codes'][0], 0, ‘first command failed')
asserts.assertEqual(results[‘return_codes'][1], 0, ‘second command failed')