2. Test Driven Development
Por que é importante?
Código de produção testável
Refatoração sem medo
Código melhor estruturado
O que não testar?
Cadastros
Leitura/Gravação de arquivos
Independência
Banco de dados
Arquivos do sistema
Arquivos de configuração
3. Mocks
Então como testar?
Mocks
Exemplo DataAccess
Testar a conversão dos Feriados do SIAP em DateTime
Biblioteca Moq.
Testes Unitários
Deve testar um único método. Todas as outras
dependências que esse método usa devem ser mockadas.
Evitar métodos estáticos
Não é possível mocká-los
DateTime.Now
Exemplo Business & DateTime.Now
Mostrar código do SIGEP (ApontamentoServicoDeve)
5. Refatoração
O código de produção
deve ser escrito o mais
simples possível para
passar
Depois de escrever
vários testes e códigos
de produção, pode-se
perceber que há códigos
duplicados ou que
poderiam ser melhores
escritos
Então chegou a hora de
refatorá-los
6. Refatorando ConsultaArquivo
Temos que testar a regra de obter o texto SQL
sem depender de um arquivo do
sistema, como?
Dependency Inversion
1º
• Vamos fazer a classe ConsultaArquivo não depender mais
dos métodos estáticos da classe File
2º
• ConsultaArquivo exigirá no construtor uma interface
IFileHelper
3º
• IFileHelper conterá 2 métodos: Existe(...) e LeTodoTexto(...)
4º
• Mockamos o IFileHelper para testar o método
ObterConsultaPorNome(...)
8. Testes de Integração
Poderíamos testar o FileHelper, mas seria um teste
de Integração e não um teste de unidade.
Seria um teste de Integração com o sistema de
arquivos do windows
Testes de Integração se caracterizam por
necessitarem de um ambiente preparado para o
teste funcionar
Acesso a arquivos
Acesso ao banco de dados
Acesso a WebServices
Testar unidades em conjunto (integradas)
9. Nomenclatura
Nome classe de teste:
NomeClasseTestadaDeve
NomeClasseTestadaNomeMetodoDeve
Nome dos métodos do teste:
Deve ser uma ação que a classe testada deve fazer
Exemplos:
PedidoBusinessDeve
Quebrar_Pedidos_Por_Representante_Quando_Parametro_Estiver_
Setado
Retornar_Apenas_Pedidos_Faturados_Da_Conta_X
Totalizar_Itens_Pedidos_Corretamente
Lancar_Excecao_Quando_Pedido_Estiver_Bloqueado
Por quê?
Facilita o entendimento sobre o que está sendo testado
Facilita para o desenvolvedor escrever o teste
10. Nomenclatura - AAA
Arrange
Organiza os objetos antes de executar o teste
Act
Executa o método que está testando
Assert
Verifica as condições para que o teste passe
Por quê?
Testes mais organizados
Testes mais limpos
Bater o olho e saber o que e como certa
funcionalidade está sendo testada
12. Muitas dependências
Classe recebe vários parametros no construtor
Talvez essa classe deva ser quebrada em mais
classes
Agrupar os parametros em outra classe e fazer o
construtor receber essa nova classe.
13. Business
Acho que não devíamos ficar presos as
Business.
Regra de negócio deve ser na Business, ok.
Mas também poderíamos criar outras classes
que a Business usa.
Exemplo: validação do Pedido é complexa
Talvez criar uma classe ValidadorPedido(Pedido)
Passar tudo o que é preciso para validar o Pedido
Na Business de Pedido chamar essa classe.
Atualmente os métodos das Business possuem
muito código e as regras estão obscuras
14. Business
Acho que poderíamos ter mais Business ao
invés de apenas Business relativas ao Model.
Exemplo CRM:
CampanhaBusinessComplement
Possui método CriarAgendamentos
Poderia ser criado uma Business relativa a
Agendamentos, pois a criação de Agendamentos
é complexa e poderia ser isolada.
15. Parametros out
ReadComplete
Por que não retornar apenas uma classe e nessa
classe colocar todos os parametros out?
CreateComplete
Por que não receber essa mesma classe que foi
criada no item anterior ao inves de vários
parametros out?
Acho que não devíamos ficar presos aos
Models.
Mais classes poderiam ser criadas para que as
responsabilidades sejam divididas.
16. Factories
São classes que funcionam como uma fábrica
de objetos.
Às vezes para instanciar uma classe, é
requerido vários parametros ou algumas
regras especificas.
Essas regras poderiam estar encapsuladas em
uma Factory
Exemplo CRM:
17. AtividadeFactory
Poderia ser criado uma classe Factory que
recebesse os objetos destacados e retornasse
uma instancia de AtividadeInfo.
18. Dependência de Web Services
Acho que não devíamos usar o Schema gerado
pelo wsdl
Se o schema mudar, toda a aplicação terá que ser
alterada
Solução
Criar nossas próprias classes
Criar camada intermediária entre nossas classes e o
schema
Converter nossas classes para o schema
Converter o schema para nossa classe
Se schema mudar, precisamos mexer apenas nessa
camada de conversão
Exemplo ruim: DualNFe usa os schemas
Exemplo bom: PortalTiss usa classes próprias
19. Referências
Software Practices, Pluralsight
Principles of Object Oriented Design
Design Patterns
Clean Code A Handbook of Agile Software
Craftsmanship, Robert C. Martin
DDD Quickly, Abel Avram & Floyd Marinescu
Resumo de DDD por Eric Evans