Princípios SOLID
André Minelli
Julho/2014
O que é software de qualidade?
Software de Qualidade:
Alta Coesão
e
Baixo Acoplamento
Sintomas da Baixa Qualidade:
Sintomas da Baixa Qualidade:
• Rigidez
Sintomas da Baixa Qualidade :
• Rigidez
• Fragilidade
Sintomas da Baixa Qualidade :
• Rigidez
• Fragilidade
• Imobilidade
Sintomas da Baixa Qualidade :
• Rigidez
• Fragilidade
• Imobilidade
Then what???
S.O.L.I.D.
To The Rescue!
Lembre-se!
Princípio ≠ Regra
Single Responsibility Principle (SRP)
Open-Closed Principle (OCP)
Liskov Substitution Principle (LSP)
Interface Segregatio...
Single Responsibility Principle (SRP)
“Uma classe deve ter somente uma
razão para mudar”
Responsabilidade = O que a classe faz?
Responsabilidade Única = Alta Coesão!
Quanto mais for feito, maior será a
chance de alterar!
Quanto mais for alterado, maior será a
chance de introduzir bugs!
Benefícios:
Benefícios:
• Reuso
Benefícios:
• Reuso
• Clareza
Benefícios:
• Reuso
• Clareza
• Nomeação
Benefícios:
• Reuso
• Clareza
• Nomeação
• Leitura Fácil
Críticas:
Críticas:
• ‘Granularidade’ da Responsabilidade
Críticas:
• ‘Granularidade’ da Responsabilidade
• Explosão de classes
DEMO
Open-Closed Principle (OCP)
“Módulos devem ser abertos para
extensão e fechados para modificação”
• Aberto para extensão
Comportamento pode ser estendido
• Fechado para modificação
Estender não significa alterar o código...
Técnicas:
Técnicas:
• Parametrização
Técnicas:
• Parametrização
• Herança
Técnicas:
• Parametrização
• Herança
• Eventos
Técnicas:
• Parametrização
• Herança
• Eventos
• Métodos de extensão
Técnicas:
• Parametrização
• Herança
• Eventos
• Métodos de extensão
• Composição
Benefícios:
Benefícios:
• Bugs apenas em código novo
Benefícios:
• Bugs apenas em código novo
• Baixo acoplamento
Críticas:
• Exige planejamento antecipado
DEMO
Liskov Substitution Principle (LSP)
“Tipos derivados devem poder
substituir seu tipo base”
Código não deve precisar saber que o
tipo atual é um sub-tipo específico
Violação Mais Comum:
if (obj is <SubType>)
O comportamento deve ser
indistinguível entre tipo base e
qualquer sub-tipo
Violações Comuns em Sub-tipos:
• Lançar novas exceções
Violações Comuns em Sub-tipos:
• Lançar novas exceções
• Pré-condições mais restritivas
Violações Comuns em Sub-tipos:
• Lançar novas exceções
• Pré-condições mais restritivas
• Pós-condições menos restritivas
Violações Comuns em Sub-tipos:
• Lançar novas exceções
• Pré-condições mais restritivas
• Pós-condições menos restritivas
...
Soluções Comuns:
Soluções Comuns:
• Documentação
Soluções Comuns:
• Documentação
• Utilizar Code Contracts For .NET
Soluções Comuns:
• Documentação
• Utilizar Code Contracts For .NET
• Criar hierarquias separadas
Soluções Comuns:
• Documentação
• Utilizar Code Contracts For .NET
• Criar hierarquias separadas
• Aplicar “Tell, Don´t As...
DEMO
Interface Segregation Principle (ISP)
“Clientes não devem ser forçados a
depender de interfaces que eles não
usam”
Não crie interfaces grandes
(com vários métodos)!
Interface menor => Alta Coesão
Benefícios:
Benefícios:
• Facilidade para implementar
Benefícios:
• Facilidade para implementar
• Mais fácil de usar
DEMO
ASP.NET MembershipProvider
Na maioria das vezes bastaria:
bool ValidateUser(string username, string password)
Versão Mais Recente:
ASP.NET Identity
Dependency Inversion Principle (DIP)
“Dependa de abstrações, não dependa
de implementações”
Técnicas:
Técnicas:
• Strategy pattern
Técnicas:
• Strategy pattern
• Adapter pattern
Técnicas:
• Strategy pattern
• Adapter pattern
• Dependency Injection
Benefícios:
Benefícios:
• Bugs apenas em código novo
• Baixo acoplamento
Benefícios:
• Bugs apenas em código novo
• Baixo acoplamento
• Testabilidade
Benefícios:
• Bugs apenas em código novo
• Baixo acoplamento
• Testabilidade
• Extensibilidade
Críticas:
• Menos controle sobre detalhes
Críticas:
• Menos controle sobre detalhes
• “Navegação” é mais difícil
DEMO
Lembre-se!
Princípio ≠ Regra
“Programar não é apenas
escrever código, assim como
cozinhar não é apenas misturar
ingredientes”
Referências:
• http://www.objectmentor.com/resources/articles/Principle
s_and_Patterns.pdf
• http://www.infoq.com/presenta...
Próximos SlideShares
Carregando em…5
×

Princípios SOLID

1.062 visualizações

Publicada em

Os princípios S.O.L.I.D. servem como guia para estruturação de software com alta qualidade

Publicada em: Software
0 comentários
1 gostou
Estatísticas
Notas
  • Seja o primeiro a comentar

Sem downloads
Visualizações
Visualizações totais
1.062
No SlideShare
0
A partir de incorporações
0
Número de incorporações
110
Ações
Compartilhamentos
0
Downloads
16
Comentários
0
Gostaram
1
Incorporações 0
Nenhuma incorporação

Nenhuma nota no slide
  • Quem já conhecia os princípios antes?
    Quem consegue citar e explicar os 5 princípios?
  • Existem várias ‘dimensões’: eficiência, testabilidade, confiabilidade, usabilidade, monitorável, manutenibilidade, clareza
    Qual a mais básica?
  • Livros de Engenharia de software sempre dizem isto, certo?
    Ligado ao relacionamento e interdependencias entre classes
    Como identificar o grau de coesão e de acoplamento?
  • Existem métricas (complexidade ciclomática, etc), mas uma forma empírica seria: pelos sintomas da falta de qualidade!
  • Rigidez: dificil de mudar
  • Rigidez: dificil de mudar
    Fragilidade: mudança em um lugar quebra ou causa bugs em vários lugares
  • Rigidez: dificil de mudar
    Fragilidade: mudança em um lugar quebra ou causa bugs em vários lugares
    Imobilidade: partes uteis que poderiam ser reaproveitadas dão muito esforço ou risco para separar do original....
  • Tudo isto é o famoso ‘código spaguetti’!
  • Uma vez identificada baixa qualidade, o que podemos fazer?
  • Principios SOLID podem ajudar!
    Descritos por Robert C. Martin, aka “Uncle Bob”
  • Não deve ser aplicado cegamente, sem bom senso!
    Dica: utilize o Princípio quando “sentir as dores”!
  • A classe é focada em apenas uma coisa (conceito, regra, serviço, etc)
  • Canivete suiço: e se for preciso trocar a faca por um abridor de lata? E se a faca quebrar?
  • Reuso = com um unica responsabilidade é maior a chance de reaproveitar
    Clareza = codigo tende a ser mais curto, sem ações inesperadas
    Nomeaçao = com um unica responsabilidade fica mais facil encontrar um nome
    Leitura facil = se é claro, tem bons nomes e curtos fica bem mais facil a leitura e entendimento
  • Reuso = com um unica responsabilidade é maior a chance de reaproveitar
    Clareza = codigo tende a ser mais curto, sem ações inesperadas, ou seja, menor chance de ter bugs!
    Nomeaçao = com um unica responsabilidade fica mais facil encontrar um nome
    Leitura facil = se é claro, tem bons nomes e curtos fica bem mais facil a leitura e entendimento
  • Reuso = com um unica responsabilidade é maior a chance de reaproveitar
    Clareza = codigo tende a ser mais curto, sem ações inesperadas, ou seja, menor chance de ter bugs!
    Nomeaçao = com um unica responsabilidade fica mais facil encontrar um nome
    Leitura facil = se é claro, tem bons nomes e curtos fica bem mais facil a leitura e entendimento
  • Reuso = com um unica responsabilidade é maior a chance de reaproveitar
    Clareza = codigo tende a ser mais curto, sem ações inesperadas, ou seja, menor chance de ter bugs!
    Nomeaçao = com um unica responsabilidade fica mais facil encontrar um nome
    Leitura facil = se é claro, tem bons nomes e curtos fica bem mais facil a leitura e entendimento
  • Reuso = com um unica responsabilidade é maior a chance de reaproveitar
    Clareza = codigo tende a ser mais curto, sem ações inesperadas, ou seja, menor chance de ter bugs!
    Nomeaçao = com um unica responsabilidade fica mais facil encontrar um nome
    Leitura facil = se é claro, tem bons nomes e curtos fica bem mais facil a leitura e entendimento
  • Granularidade: Responsabilidade pode ser tão grande ou tão pequena qto se queira! Dica: pensar em razões para mudar
    Explosão: pode dificultar o entendimento; porem não existirá muito mais código do que se houvessem poucas classes – a logica geral é a mesma; e a clareza, tende a facilitar
  • Granularidade: Responsabilidade pode ser tão grande ou tão pequena qto se queira! Dica: pensar em razões para mudar
    Explosão: pode dificultar o entendimento; porem não existirá muito mais código do que se houvessem poucas classes – a logica geral é a mesma; e a clareza, tende a facilitar
  • Granularidade: Responsabilidade pode ser tão grande ou tão pequena qto se queira! Dica: pensar em razões para mudar
    Explosão: pode dificultar o entendimento; porem não existirá muito mais código do que se houvessem poucas classes – a logica geral é a mesma; e a clareza, tende a facilitar
  • ETL básico: CSV para banco de dados (é incrível como isto ainda é comum...)

    Depois do DEMO:
    SRP é a ‘mãe’ de todos os demais princípios SOLID. Os demais princípios são como técnicas ou heurísticas para aplicar SRP
  • Usar ‘if’ ou ‘switches’ ou incluir código diretamente não deve ser a primeira opção!
    Exceto para corrigir bugs
  • É necessário preparar seu código para OCP!
  • Pode ser sofisticado ao usar delegates/lambdas
  • Herança: polimorfismo/sobrescrição de métodos (problema: necessário marcar métodos como virtual); Template Method Pattern;
  • Eventos: sinaliza ocorrências de interesse, expondo informaçoes e ate permitindo alterar o fluxo (ex: FormClosing) – é necessário definir quais momentos serão interessantes...
  • Métodos de extensão: OCP por definição, já que a classe permanece intacta; mas nao comece a criar bibliotecas de classes estáticas (testabilidade vai sofrer!)! 

  • Composição: Strategy Pattern; Proxy Pattern; Decorator Pattern; Chain of responsability Pattern
  • Não introduz bugs
  • Não introduz bugs em código existente, já testado, pois estes são minimamente alterados
  • Reduz gráfico de dependência de cada classe
  • Pensar em tudo que pode vir a ser necessário, no futuro, gera desperdício de tempo (a menos que vc seja um desenvolvedor de frameworks)
  • Novo requisito: adicionar o total de registros processados
  • Desconfie quando precisar usar “if (x is T)” – você pode estar violando o LSP!!
  • Exceto se forem exceções derivadas de exceções lançadas pelo tipo base
  • Ex: se parâmetro pode ser nulo no pai, o filho não pode recusar um parâmetro nulo
  • Ex: se o retorno de um método nunca era nulo no tipo pai, o filho não pode retornar nulo no mesmo método.
  • Ex: propriedade readonly no tipo pai passa a ser mutável no tipo derivado
  • Auxilia nos 3 últimos problemas (pre-cond, pos-cond e invariantes)
  • Auxilia principalmente no primeiro problema
    Relacionado ao próximo principioo (ISP)
  • Em vez de perguntar algo sobre o estado de um objeto, decidir o que fazer e então pedir ao objeto para fazer, peça diretamente ao objeto para fazê-lo, e deixe a decisão por conta do próprio objeto (relacionado ao SRP)
  • Interfaces grandes em geral indicam violação do SRP – está fazendo coisas demais!
  • Interface menor = alta coesão
  • Facil pra quem implementa
  • Menos coisas para se entender, portanto o cliente tem menos chance de errar ao usar
  • Demo na Web ->
  • 7 propriedades e 17 métodos, se eu contei direito!!!
    Observem: usa herança
  • Mistura de Façade (UserManager) com Strategy (IUserStore, IUserPasswordStore, etc) - usa composição
  • Utilizar uma abstração em vez de uma implementação, para facilitar a substituição de implementações
  • Implementações nem sempre são feitas ‘sob medida’
  • Uso de um ‘container’, responsável por ‘resolver’ as dependências (por construtor, por um ‘setter’, por uma interface)
  • Mesmos do OCP – forma especializada de OCP
  • Testes de unidade ficam mais fáceis: pode-se substituir uma dependência para testar uma classe em isolamento
  • Possibilidade de se alterar implementações (usando Decorator, Proxy, Interception, etc)
  • Pode comprometer desempenho, por exemplo
  • Encontrar as dependencias ao ler o código fica mais dificil, principalmente quando existem várias implementações da mesma abstração
  • (Antes de ir para próximo slide) Vale reforçar...
  • NÃO FIQUE OBCECADO!
    Novamente: utilize o Princípio quando “sentir as dores”!
  • Os melhores cozinheiros sabem a ordem de preparo, as quantidades corretas, conseguem adaptar receitas e utilizar ingredientes alternativos, etc...
    A analogia entre programação e cozinha é bastante útil:
    -panelas e ingredientes corretos fazem bastante diferença
    -pense em quem será servido
    -receba feedback dos pratos servidos
  • Princípios SOLID

    1. 1. Princípios SOLID André Minelli Julho/2014
    2. 2. O que é software de qualidade?
    3. 3. Software de Qualidade: Alta Coesão e Baixo Acoplamento
    4. 4. Sintomas da Baixa Qualidade:
    5. 5. Sintomas da Baixa Qualidade: • Rigidez
    6. 6. Sintomas da Baixa Qualidade : • Rigidez • Fragilidade
    7. 7. Sintomas da Baixa Qualidade : • Rigidez • Fragilidade • Imobilidade
    8. 8. Sintomas da Baixa Qualidade : • Rigidez • Fragilidade • Imobilidade
    9. 9. Then what???
    10. 10. S.O.L.I.D. To The Rescue!
    11. 11. Lembre-se! Princípio ≠ Regra
    12. 12. Single Responsibility Principle (SRP) Open-Closed Principle (OCP) Liskov Substitution Principle (LSP) Interface Segregation Principle (ISP) Dependency Inversion Principle (DIP)
    13. 13. Single Responsibility Principle (SRP) “Uma classe deve ter somente uma razão para mudar”
    14. 14. Responsabilidade = O que a classe faz? Responsabilidade Única = Alta Coesão!
    15. 15. Quanto mais for feito, maior será a chance de alterar! Quanto mais for alterado, maior será a chance de introduzir bugs!
    16. 16. Benefícios:
    17. 17. Benefícios: • Reuso
    18. 18. Benefícios: • Reuso • Clareza
    19. 19. Benefícios: • Reuso • Clareza • Nomeação
    20. 20. Benefícios: • Reuso • Clareza • Nomeação • Leitura Fácil
    21. 21. Críticas:
    22. 22. Críticas: • ‘Granularidade’ da Responsabilidade
    23. 23. Críticas: • ‘Granularidade’ da Responsabilidade • Explosão de classes
    24. 24. DEMO
    25. 25. Open-Closed Principle (OCP) “Módulos devem ser abertos para extensão e fechados para modificação”
    26. 26. • Aberto para extensão Comportamento pode ser estendido • Fechado para modificação Estender não significa alterar o código original diretamente
    27. 27. Técnicas:
    28. 28. Técnicas: • Parametrização
    29. 29. Técnicas: • Parametrização • Herança
    30. 30. Técnicas: • Parametrização • Herança • Eventos
    31. 31. Técnicas: • Parametrização • Herança • Eventos • Métodos de extensão
    32. 32. Técnicas: • Parametrização • Herança • Eventos • Métodos de extensão • Composição
    33. 33. Benefícios:
    34. 34. Benefícios: • Bugs apenas em código novo
    35. 35. Benefícios: • Bugs apenas em código novo • Baixo acoplamento
    36. 36. Críticas: • Exige planejamento antecipado
    37. 37. DEMO
    38. 38. Liskov Substitution Principle (LSP) “Tipos derivados devem poder substituir seu tipo base”
    39. 39. Código não deve precisar saber que o tipo atual é um sub-tipo específico
    40. 40. Violação Mais Comum: if (obj is <SubType>)
    41. 41. O comportamento deve ser indistinguível entre tipo base e qualquer sub-tipo
    42. 42. Violações Comuns em Sub-tipos: • Lançar novas exceções
    43. 43. Violações Comuns em Sub-tipos: • Lançar novas exceções • Pré-condições mais restritivas
    44. 44. Violações Comuns em Sub-tipos: • Lançar novas exceções • Pré-condições mais restritivas • Pós-condições menos restritivas
    45. 45. Violações Comuns em Sub-tipos: • Lançar novas exceções • Pré-condições mais restritivas • Pós-condições menos restritivas • Invariantes menos restritivos
    46. 46. Soluções Comuns:
    47. 47. Soluções Comuns: • Documentação
    48. 48. Soluções Comuns: • Documentação • Utilizar Code Contracts For .NET
    49. 49. Soluções Comuns: • Documentação • Utilizar Code Contracts For .NET • Criar hierarquias separadas
    50. 50. Soluções Comuns: • Documentação • Utilizar Code Contracts For .NET • Criar hierarquias separadas • Aplicar “Tell, Don´t Ask” Principle
    51. 51. DEMO
    52. 52. Interface Segregation Principle (ISP) “Clientes não devem ser forçados a depender de interfaces que eles não usam”
    53. 53. Não crie interfaces grandes (com vários métodos)! Interface menor => Alta Coesão
    54. 54. Benefícios:
    55. 55. Benefícios: • Facilidade para implementar
    56. 56. Benefícios: • Facilidade para implementar • Mais fácil de usar
    57. 57. DEMO
    58. 58. ASP.NET MembershipProvider
    59. 59. Na maioria das vezes bastaria: bool ValidateUser(string username, string password)
    60. 60. Versão Mais Recente: ASP.NET Identity
    61. 61. Dependency Inversion Principle (DIP) “Dependa de abstrações, não dependa de implementações”
    62. 62. Técnicas:
    63. 63. Técnicas: • Strategy pattern
    64. 64. Técnicas: • Strategy pattern • Adapter pattern
    65. 65. Técnicas: • Strategy pattern • Adapter pattern • Dependency Injection
    66. 66. Benefícios:
    67. 67. Benefícios: • Bugs apenas em código novo • Baixo acoplamento
    68. 68. Benefícios: • Bugs apenas em código novo • Baixo acoplamento • Testabilidade
    69. 69. Benefícios: • Bugs apenas em código novo • Baixo acoplamento • Testabilidade • Extensibilidade
    70. 70. Críticas: • Menos controle sobre detalhes
    71. 71. Críticas: • Menos controle sobre detalhes • “Navegação” é mais difícil
    72. 72. DEMO
    73. 73. Lembre-se! Princípio ≠ Regra
    74. 74. “Programar não é apenas escrever código, assim como cozinhar não é apenas misturar ingredientes”
    75. 75. Referências: • http://www.objectmentor.com/resources/articles/Principle s_and_Patterns.pdf • http://www.infoq.com/presentations/design-principles- code-structures • http://www.slideshare.net/Hitheshh/solid-31661700 • www.craigberntson.com/docs/SOLID.pptx • http://channel9.msdn.com/Events/TechEd/NorthAmerica/2 014/DEV-B315 • http://www.cuttingedge.it/blogs/steven/pivot/entry.php?id =92 • http://research.microsoft.com/en-us/projects/contracts/ • https://simpleinjector.codeplex.com/wikipage?title=Advanc ed-scenarios#Interception

    ×