Se estou escrevendo testes de unidade em python (usando o módulo unittest), é possível gerar dados de um teste que falhou, para que eu possa examiná-lo para ajudar a deduzir o que causou o erro? Estou ciente da capacidade de criar uma mensagem personalizada, que pode conter algumas informações, mas às vezes você pode lidar com dados mais complexos, que não podem ser facilmente representados como uma string.
Por exemplo, suponha que você tenha uma classe Foo e esteja testando uma barra de método, usando dados de uma lista chamada testdata:
class TestBar(unittest.TestCase):
def runTest(self):
for t1, t2 in testdata:
f = Foo(t1)
self.assertEqual(f.bar(t2), 2)
Se o teste falhou, eu poderia querer produzir t1, t2 e / ou f, para ver por que esses dados específicos resultaram em uma falha. Por saída, quero dizer que as variáveis podem ser acessadas como quaisquer outras variáveis, após o teste ter sido executado.
fonte
msg
for usado, substituirá a mensagem de erro normal. Para sermsg
anexado à mensagem de erro normal, você também precisa definir TestCase.longMessage como TrueTrue
.Usamos o módulo de registro para isso.
Por exemplo:
Isso nos permite ativar a depuração para testes específicos que sabemos que estão falhando e para os quais desejamos informações adicionais de depuração.
Meu método preferido, entretanto, não é gastar muito tempo depurando, mas escrevendo testes mais refinados para expor o problema.
fonte
foo
? Uma função separada? Uma função de método deSomeTest
? No primeiro caso, uma função pode ter seu próprio logger. No segundo caso, a outra função do método pode ter seu próprio logger. Você sabe como ologging
pacote funciona? Vários loggers é a norma.Você pode usar instruções de impressão simples ou qualquer outra maneira de escrever no stdout. Você também pode chamar o depurador Python em qualquer lugar em seus testes.
Se você usa nariz para executar seus testes (o que eu recomendo), ele coletará o stdout para cada teste e apenas o mostrará se o teste falhar, para que você não tenha que conviver com a saída desordenada quando os testes passarem.
O nariz também tem opções para mostrar automaticamente as variáveis mencionadas em declarações ou para chamar o depurador em testes com falha. Por exemplo
-s
(--nocapture
) impede a captura de stdout.fonte
print
elog.debug()
um ao lado do outro, e habilito explicitamente oDEBUG
registro na raiz dosetUp()
método, mas apenas aprint
saída é exibida.nosetests -s
mostra o conteúdo de stdout se houver um erro ou não - algo que considero útil.Não acho que seja exatamente isso que você está procurando, não há como exibir valores de variáveis que não falhem, mas isso pode ajudá-lo a chegar mais perto de produzir os resultados da maneira que deseja.
Você pode usar o objeto TestResult retornado pelo TestRunner.run () para análise e processamento de resultados. Particularmente, TestResult.errors e TestResult.failures
Sobre o objeto TestResults:
http://docs.python.org/library/unittest.html#id3
E algum código para apontar a direção certa:
fonte
Outra opção - inicie um depurador onde o teste falhar.
Tente executar seus testes com Testoob (ele executará seu pacote de teste de unidade sem alterações), e você pode usar a opção de linha de comando '--debug' para abrir um depurador quando um teste falhar.
Esta é uma sessão de terminal no Windows:
fonte
O método que uso é muito simples. Eu apenas registro como um aviso para que ele realmente apareça.
fonte
Acho que estou pensando demais nisso. Uma maneira que descobri para fazer o trabalho é simplesmente ter uma variável global, que acumula os dados de diagnóstico.
Algo assim:
Obrigado pelas respostas. Eles me deram algumas idéias alternativas sobre como registrar informações de testes de unidade em python.
fonte
Use o registro:
Uso:
Se você não definir
LOG_FILE
, o registro terá que ser feitostderr
.fonte
Você pode usar
logging
módulo para isso.Portanto, no código de teste de unidade, use:
Por padrão, avisos e erros são enviados para
/dev/stderr
, portanto, devem estar visíveis no console.Para personalizar registros (como formatação), tente o seguinte exemplo:
fonte
O que eu faço nesses casos é ter um
log.debug()
com algumas mensagens em meu aplicativo. Uma vez que o nível de registro padrão éWARNING
, essas mensagens não aparecem na execução normal.Então, no teste de unidade, altero o nível de registro para
DEBUG
, de modo que tais mensagens sejam mostradas durante a execução.Nos testes de unidade:
Veja um exemplo completo:
daikiri.py
Ou seja , uma classe básica que implementa um Daikiri com seu nome e preço. Existe um métodomake_discount()
que retorna o preço daquele daikiri específico após a aplicação de um determinado desconto:Então, eu crio um teste de unidade
test_daikiri.py
que verifica seu uso:Então, quando eu o executo, recebo as
log.debug
mensagens:fonte
inspect.trace permitirá que você obtenha variáveis locais depois que uma exceção for lançada. Você pode então envolver os testes de unidade com um decorador como o seguinte para salvar essas variáveis locais para exame durante a autópsia.
A última linha imprimirá os valores retornados onde o teste foi bem-sucedido e as variáveis locais, neste caso x, quando ele falhar:
Har det gøy :-)
fonte
Que tal capturar a exceção gerada a partir da falha de asserção? Em seu bloco de captura, você pode enviar os dados da maneira que quiser, em qualquer lugar. Então, quando você terminar, poderá lançar novamente a exceção. O executor de teste provavelmente não saberia a diferença.
Isenção de responsabilidade: eu não tentei isso com a estrutura de teste de unidade do Python, mas tentei com outras estruturas de teste de unidade.
fonte
Admitindo que não tentei, o recurso de registro do testfixtures parece bastante útil ...
fonte
Expandindo a resposta de @FC, isso funciona muito bem para mim:
fonte