Maxi Contieri Profile picture
Aug 24, 2020 49 tweets 18 min read Read on X
Knowing the problems is the first step to solving them.

A thread on #CodeSmells 🧵⬇️📅
#CodeSmell 01: Your objects are a bunch of public attributes

Problem: en.wikipedia.org/wiki/Anemic_do…

Solutions:
1) Find Responsibilities.
2) Protect your attributes.
3) Hide implementations
4) Delegate
#CodeSmell 02: Code has lots of comments

Problem: Comments are coupled to implementation

Solutions:
1) Refactor methods
2) Rename methods to more declarative unes
3) break methods
4) If a comment describe what a method does. Just name the method with this description
#CodeSmell 03: Functions are too long

Problems: Low Cohesion, High coupling, Difficult to read

Solutions:
1) Refactor
2) Create small objects dealing with some of the tasks. Unit test them
3) Compose methods
#CodeSmell 04: Function receiving too many arguments

Problems: Low maintainability. Low Reuse. Coupling

Solutions
1) Find cohesive relations among arguments
2) Create a "context"
3) Consider using a MethodObject Pattern
4) Avoid "basic" Types, Specially arrays. Think on objects
#CodeSmell 05: Object with too many attributes

Problems: Same as #CodeSmell 04

Solutions
1) Find methods related to attributes
2) Cluster this methods
3) Break the object related to those clusters
4) Find real objects related to this new objects and replace existing references
#CodeSmell 06: Constants and Magic Numbers

Problems: Coupling, Low testability, Low readability

Solutions
1) Replace constants with parameters so you can mock them
2) The constant definition is often a different object than the constar (ab)user
3) Group the cohesive parameters
#codesmell 07: switch/case/elseif/else/if statements

Problems:
Two Many decisions together
Coupling
Duplicated code
Nulls

Solutions
1 polymorphism
2 Open closed principle
3 state pattern
#codesmell 08: a Small change in requirements is a big change on model

Problems:
Coupling

Solutions:
1 refactor and isolate what is changing
2 depend on a interfaces
3 avoid ifs
Codesmell 09: Long chains of collaborations

Problems:
Coupling
Break encapsulation

Solutions:
1 Think about en.wikipedia.org/wiki/Law_of_De…
2 Create indirect collaborations
3 Create higher level messages

Wrong: dog->feet-> move
Right: dog->run
Codesmell 10: Two sibling classes sharing implementation but not fulfilling 'behavesLike' relation

Problems:
Accidental coupling
Liskov's substitution

Solutions:
1 Refactor what they have in common.
2 Use Composition and break hierarchy
#Codesmell 11: Avoid string abusers

Problems:
Too many parsing, exploding, regex, strcomp, strpos and string manipulation functions

Solutions:

1 Work with objects
2 Replace strings with data structures dealing with object relations
3 Go back to Perl :)
#Codesmell 12: Avoid protected methods

Problems:
Concrete protected methods are a code smell of subclassification for reuse purposes

Solutions:
1 Favor composition
2 Don't subclassify
3 extract behaviour
4 Use traits (if available)
#CodeSmell 13: Objects referenced via ids

Problems:
Accidental Coupling
Bad Models
Premature Optimization

Solutions:
1 Do not Mix Ids with objects.
2 Ids are only necessary when giving reference to an external system.
3 Objects know objects by references. not by Ids
#codesmell 14: model objects persisting/retrieving

Problems
coupling
Premature optimization
No testability

Solutions:
1 Separation of concerns
2 Decoupling persistence
3 Domain driven design
#codesmell 15: Cyclomatic complexity:

Problems:
too many branches or loops
Readability

Solutions:
Break up functions into smaller functions
Create private functions
Create a Method Object
#Codesmell 16: Overriding concrete implementation
Subclass deciding NOT to do what is declared by super

Problems:
Bad Cohesion
Coupling
Subclassing for code reuse

Solutions:
Break inheritance
Move default implementation down
Favor Composition
#CodeSmell 17: Naming a variable is a Bad Naming smell
Names too abstract referring to metamodel like:
-Abstract
-Value
-Result
-Object
-Outcome
-Input

Are code smells.
Find which real world roles are misrepresented on your code
#CodeSmell 18: avoid too abstract names.
Implementative Naming is a code smell.

Repository is an awful name.
Think about real world names like:
-schedule
-notebook
-diary
-journal
CodeSmell #19: Coupling to other objects implementation

When an object is coupled to implementation and not to protocol any change will cause ripple effect.

a Public attribute is a smell of this.

The outcome might be a funny en.wikipedia.org/wiki/Object_or…
CodeSmell: #20: Using nulls

Nulls are an anti pattern
You can use nulls on databases because null don't execute, but interpreting this nulls is impossible since it might represent different meanings.

Remember Null's autor regret and have mercy on him
CodeSmell: #21 Repeated Code
Problems:
-Coupling
-Maintainability
-DRY

Solutions:
-Find the missing abstraction in real world and extract the code there
-Use the new abstraction
CodeSmell: #22 Caches
Problems
-Coupling
-Invalidation brings functional problems
-Premature Optimization
-!Testability
-Global references

Solutions
-Avoid General Purpose Cach
-Benchmark
-Find Bottlenecks
-Create functional contexts and proxies (object in the middle)
-Ask Knuth
#CodeSmell: 23 Missed Preconditions
Problems
-Not fail fast
-Contract breaking
-Hard to debug
-Bad cohesion

Solutions
-Create strong preconditions
-Raise exceptions
-Fail Fast
-Defensive Programming
#CodeSmell 24: Magic Numbers
Problems:
-Maintainability
-Fear to change

Solutions:
-Create constants with long, intention revealing values
-Do not add those constants as static class constants, this will prevent from testing
--Test must be in full control to "play" w/t constants
#codesmell 25:
Trying to build complex solutions for a simple functional problem

with excellent models there's a mapping between code and functional complexity

A simple problem in real world should be fixed simple

If building complex algorithms caches go back

Solve it with PO
#CodeSmell 26: Avoid excessive Pattern Naming

A class StrategyFactoryDispatcherStateHandler is a code smell of coupling and low cohesion.

A class with more than 1 pattern on its name is a code smell of bad coupled protocol
#CodeSmell 27: Code that autocorrects without warnings

Some programming languages make invalid coercions hiding the source of errors and deferring debugging (tracing these errors is almost impossible)

Examples:

-new Date(31,02,2020)
- 1 + 'Hello'
- !3

All 3 are errors
#CodeSmell 28: Inconsistent Names

In order to fulfill least surprise principle all names mus be consistent.

For example if you have a method open() you should use close(), not doclose(), remove(), finish() etc

#Refactorings are free nowadays so must do it whenever you encouter
#CodeSmell 29: Primitive Obsession

Using Data types to represent anemic Objects

Examples:
a Date created from 3 integers
a Coordinate create by two floats
an integer to represent money

Don't be afraid to create small objects.
They fall fast and don't coerce !
#CodeSmell 30: Refused Bequest

A subclass overrides most of superclass protocol

Problems:
-Bad design
-Coupling
-Inheriting for code sharing (accidental)
-Very Low cohesion

Solution:
-Move away subclass
-Use composition or traits
-Use interface segregation
#CodeSmell 31: Library Objects

an Object that performs lots of interactions with its arguments but does not call self.

Problems:
-Bad Cohesion
-Long Methods

Solutions:
-Split into method object
-Create an object for every different function
-Change the name: DO NOT USE HELPER
#CodeSmell 32: Polymorphic Shame

Methods that do the same thing but have different signatures for what they do

ej: listSort() vs arraySort()

Problems:
-Ifs/cases/switchs
-Violate Open/Closed Principle

Solutions:
-rename them to sort() if possible
-change language (if not)
#CodeSmell 33: Message Chains

A method calling a different method which calls a different method which calls a different method...

Problems:
-Coupling
-Fragility
-Demeter's Law
-Information (not) hiding

Solutions:
-shortcuts
-create chain methods

Dog>Leg>Move
Dog>MoveLeg
#CodeSmell 34: Parallel inheritance hierarchies

Problems:
-Complexity
-Repeated Code
-Coupling

Solutions:
-Composition instead of inheritance
-Abstract Factory
-Compact Code
#CodeSmell 35: Constructors calling super

Problems:
-Inheritance for code reuse
-implementation on abstract classes
-Deep Hierarchies

Solutions:
-Remove abstract constructors and their associated attributes
-Full initialization should be done on concrete
-Refactor Hierarchy
#CodeSmell 36: Do not use globals.

Seems pretty obvious but classes and namespaces are also globals :)

Problems:
-Coupling
-Ripple Effect
-Singletons

Solutions:
-Talk to a context provider
-Mock this providers on tests
#CodeSmell 37: Many Mixed Exceptions

In a try/catch block exceptions should be independent and orthogonal and at the same level than code.

Do not mix low/high level exceptions

try{}
catch Exception
catch Specific

Borrowed from @MattCodeJourney here
#CodeSmell 39: Static Methods

Problems:
-Coupling to globals (classes)
-Not Mockable
-Violation on Solid's SOR (class sole responsibility is to create instances)
-Lack of Maintainability

Solutions:
-Move the method to instance in a smaller class
-Refactor
-Dependency injection
#CodeSmell 40: Todo: Fix after demos

Proof of concepts, prototypes and MVP are excellent for exploration and sales

If you encounter this kind of #technicaldebt, run away !

Prototype code should be discarded
There's a proverb stating second time we implement sth we do it better
#CodeSmall 41: Unreferenced Classes

Problems
-Dead Code
-Metaprogramming
-Only referenced by tests

Solutions
-Remove class
--If some test fails there's metaprogramming #smell. Make reference explicit instead
--If production fails may god help you
CodeSmell 42: Unreferenced Methods (See above)

Problems:
-Dead Code
-Metaprogramming
-Only referenced by tests

Solutions
-Remove method
--If some test fails there's metaprogramming #smell. Make call explicit instead
--If production fails may god help you

Avoid Metaprogramming
CodeSmell 43: Hang from classes

Everytime you hear the expression is someone buying #techdebt

Problems
-Lots of coupling

Solutions:
-Do not subclassify concrete classes
-Do not reuse code by subclassing
-Do not violate Solid principles
-Be mature when coding
#CodeSmell 44: Shotgun Surgery

A small business change impacts on lots of different objects.

Problems:
-Low Cohesion
-Coupling

Solutions:
-Encapsulate what changes and use Single Responsibility Principle
-Delegate
#CodeSmell 45: No Behavior at all

-Choose 1 rand source file
-Count the lines with real behavior methods (no, setters are not behavior)

75% of lines min should have business behavior
If not you're creating anemic models
Try imperative languages instead
They are not bad at all
#CodeSmell 46: Class with just one method.

Either this method is large
-It should be splitted
or is small
-it is probably a masked global

The class sure has #lowcohesion
#CodeSmell 47: Cohesive parameters

Two related parameters not working together

Wrong:
moneyMovements($dateFrom, )
//Valitations

Right:
moneyMovements($dateRange)

new DateRange($since, )
//Validation

These small objects are not obvious !
#codeSmell 48: Globals

Avoid globals.
They generate coupling, side effects and makes testing very difficult.

BTW: Classes are globals (even if you can use namespaces)
Their coupling can be avoided with #dependencyinjection and #factories

• • •

Missing some Tweet in this thread? You can try to force a refresh
 

Keep Current with Maxi Contieri

Maxi Contieri Profile picture

Stay in touch and get notified when new unrolls are available from this author!

Read all threads

This Thread may be Removed Anytime!

PDF

Twitter may remove this content at anytime! Save it as PDF for later use!

Try unrolling a thread yourself!

how to unroll video
  1. Follow @ThreadReaderApp to mention us!

  2. From a Twitter thread mention us with a keyword "unroll"
@threadreaderapp unroll

Practice here first or read more on our help page!

More from @mcsee1

Jun 3, 2021
Code Smell 04 - String Abusers

Too many parsing, exploding, regex, strcomp, strpos and string manipulation functions.
TL;DR: Use real abstractions and real objects instead of string accidental manipulation.
😔 Problems

- Complexity
- Readability
- Maintainability
- Lack of Abstractions
Read 13 tweets
Dec 31, 2020
My *personal* recommendations on who to follow on 2021!

A Thread 🧵 on great content and great people on Twitter.
Happy new year to all of you!

(A-Z) 1/Many
@AlejandroPiad (Alejandro Piad Morffis)

Alejandro writes interesting content on software development and machine learning.
He teaches Computer Science and his content is great.
I love interacting with him.
@allenholub (Allen Holub)

Allen is a DDD passionate. His opinions are very strong and accurate.
I enjoy his development tips AND management and agile humor a lot.
I liked very much his courses on LinkedIn.
Read 29 tweets
Oct 4, 2020
Another 🧵 on #productivitytip and #LifeHacks

As usual one each day.

Disclaimer: Opinions are my own. I don't have the truth revealed.

I learn a lot with your replies so please contribute and discuss !
#productivitytip 1: Remove notifications

1 - Check your phone after a couple of hours.
2 - Keep an eye on the app with the most notifications
3 - Block them
4 - Don't fear #FOMO. Deal with it
5 - Repeat once a day.

Watch #TheSocialDilemma
#productivitytip 2: Slice your time

1 - Use blocks of time without interruptions (timeboxing).
2 - My favorite is @PomodoroTech.
3 - if you come across new tasks just write them down.
4 - Don't multitask.
5 - You cannot switch until time is up.
6 - 25 minutes it's a good slice.
Read 11 tweets
Sep 10, 2020
Any problem in computer science can be solved with another level of indirection

-@drdavidawheeler
You can mass-produce hardware; you cannot mass-produce software; you cannot mass-produce the human mind.

-Michio Kaku
I invented the term ‘object oriented’, and C++ was not what I had in mind

-Alan Kay
Read 122 tweets
Aug 29, 2020
Sometimes an idea fits in 280 characters

a 🧵 on Great #SoftwareEngineering great #quotes

One each day.
For each desired change, make the change easy (warning: this may be hard), then make the easy change

-@KentBeck
There are only two hard things in Computer Science: cache invalidation and naming things.

-Phil Karlton
Read 186 tweets
Aug 9, 2020
I’m creating a thread on #softwaredesing. One tip per day.
Until no advices are left or I reach thread limit. Whatever happens in the first time.
Tip 01: Do not subclassify concrete classes.
Tip 02: Variable names should indicate role. Never type
Read 67 tweets

Did Thread Reader help you today?

Support us! We are indie developers!


This site is made by just two indie developers on a laptop doing marketing, support and development! Read more about the story.

Become a Premium Member ($3/month or $30/year) and get exclusive features!

Become Premium

Don't want to be a Premium member but still want to support us?

Make a small donation by buying us coffee ($5) or help with server cost ($10)

Donate via Paypal

Or Donate anonymously using crypto!

Ethereum

0xfe58350B80634f60Fa6Dc149a72b4DFbc17D341E copy

Bitcoin

3ATGMxNzCUFzxpMCHL5sWSt4DVtS8UqXpi copy

Thank you for your support!

Follow Us!

:(