working with legacy code 3
TRANSCRIPT
![Page 1: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/1.jpg)
Working with legacy code
![Page 2: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/2.jpg)
Extract Interface
Utilizar interface ao invés de classes concretas podem ajudar no design, no polimorfismo e especialmente em testes.
![Page 3: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/3.jpg)
public class PayTransaction extends Transaction { public PayTransaction (Database db,
TransactionRecorder log) { public void run() { ... } } }
![Page 4: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/4.jpg)
Parâmetros como Database db e TransactionRecorder log podem ser opcionais em um testes, na verdade criaremos superclasses com uma implementação simples ou vazia dos métodos existentes.
Também as interface costumam melhorar o modelo do código, pois pensa-se primeiro nos métodos necessários sem sua implementação e nos parâmetros necessário.
![Page 5: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/5.jpg)
• A maioria das IDEs atuais traz ferramentas como Extract Interface. Procure usá-las especialmente quando há muitas implementações da classe.
• Cuidado com os métodos estáticos, pois eles não podem fazer parte da interface.
• Procure extrair os métodos de forma incremental à medida que se escreve testes para os mesmos(Testes da classe final).
![Page 6: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/6.jpg)
Passo a passo
• Criar a interface com nome apropriado sem nenhum método.
• Implementar a interface nas classes desejadas
• Substituir as chamadas das classes pela da interface.
• O código não irá compilar enquanto não se extrair as assinaturas dos métodos para interface.
![Page 7: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/7.jpg)
Extract Implementer
Mesma finalidade de Extract Interface, no entanto, a classe se tornará a Interface e a será criada uma cópia idêntica da classe atual, mas com outro nome.
![Page 8: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/8.jpg)
Razões
• Em geral o nome da classe atual é o nome ideal para interface, pois é nela que contém a “idéia”, e a classe é como a idéia será executada.
• Muitos usam prefixos em interfaces, no entanto, é muito ruim trabalhar com tais nomes pois fere o princípio conhecido como “well-named”.
![Page 9: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/9.jpg)
“This class is too big and I don't want it to get any bigger”
![Page 10: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/10.jpg)
RuleParser
- current: string- variables: Hasmap- currentPosition: int+ evaluate(string): int+ branchExpression(Node left, Node right): int+ causalExpression(Node left, Node right): int+ variableExpression(Node node): int+ nextTerm(): string- hasMoreTerms(): boolean+ addVariable(string name, int value)
![Page 11: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/11.jpg)
evaluate branchingExpression nextTerm addVariable
causalExpression hasMoreTerms
variableExpression
valueExpression
Em geral, as classe apresentam nomes com prefixos ou sufixos similares como segue abaixo:
![Page 12: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/12.jpg)
RuleEvaluator+ evaluate(string)+ addVariable(string, int)
SymbolTable+ addVariable(string, int)
RuleParser+ parse(string): Expression
TermTokenizer+ nextTerm(): string+ hasMoreTerms: boolean
Expression+ evaluateWith(SymbolTable)
![Page 13: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/13.jpg)
Heurística
• Group methods – agrupar métodos por nome ou funcionalidade. É pouco custoso e facilita o entendimento em grandes classes.
• Look at Hidden Methods – Classes grandes costumam ter diversos métodos privados, se necessário converta-os em públicos para testes. Muitas vezes chega-se a conclusão de criar uma nova classe com esses métodos.
![Page 14: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/14.jpg)
Heurística
• Look for decisions that can change – foque nas tomadas de decisões dos métodos já criados, verifique se usa conexão com banco de dados, grandes APIs, hard-coded.
• Look for internal relationships – Em geral classes muito grandes com diversos atributos e métodos não são chamam um pelo outro em todos os lugares, então, conclui que pode-se descobrir quais métodos devem ser testados.
![Page 15: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/15.jpg)
Heurística
• Look for the Primary Resposibility – Tente descrever uma classe em uma única fase.
• When all else fails, do some Scratch Refactoring.
• Focus on the current work – Mude apenas o necessário. Não se trata de uma reforma completa, apenas uma refatoração suficiente para que haja maior sentimento de confiança na alteração real.
![Page 16: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/16.jpg)
Feature sketch• É um esquema muito útil e simples
para descobrir o relacionamento interno entre os métodos e atributos das classes.
• Agrupa-se os métodos e atributos por similaridade de nome ou funcionalidade.
![Page 17: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/17.jpg)
Reservation- duration: int- dailyRate: int- date: Date- customer: Costumer- fees: List+ extend(days)+ extendForWeek()+ addFee(FeeRider)<<delegates>>- getPrincipalFee(): int+ getTotalFee() :int+ getAdditionalFee(): int
![Page 18: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/18.jpg)
duration
getPrincipalFee
extend
dailyRateextendForWeek
date
customer
getTotalFeegetAdditionalFees
fees
addFee
Esquema da classe Reservation
![Page 19: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/19.jpg)
duration
getPrincipalFee
extend
dailyRate
extendForWeek
date
customer
getTotalFeegetAdditionalFees
fees
addFee
Métodos aglomerados em Reservation
![Page 20: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/20.jpg)
duration
getPrincipalFee
extend
dailyRate
extendForWeek
date
customer
getTotalFee
getAdditionalFees
fees
addFee
Métodos aglomerados em outra classe
![Page 21: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/21.jpg)
Interface segragation Principle
Grandes classes que implementam interfaces geralmente não usufruem de todos os métodos, então, é mais interessante criar diversas interfaces menores e implementar quantas forem necessárias nas classes.
![Page 22: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/22.jpg)
...que ao adicionar novas funcionalidades, acima de tudo, o design atual já funcionava. Sejam classes grandes ou sem padrões, elas atualmente exercem funções e muitas vezes de maneira eficiente.
Ao adicionar novas funcionalidades lembre-se...
![Page 23: Working with legacy code 3](https://reader034.vdocument.in/reader034/viewer/2022052316/55946e061a28abea718b4609/html5/thumbnails/23.jpg)
Working with Legacy Code by Michael Feather
Recomendação do autor:• Livro Refactoring: Improving the Design of Existing Code
(Martin Fowler)