Victor works on the Angular team at Google. He is interested in functional programming, the Web platform, and client-side applications. Being a language nerd he spends a lot of my time playing with Smalltalk, JS, Dart, Scala, Haskell, Clojure, Ruby, and Ioke. Victor is a DZone MVB and is not an employee of DZone and has posted 45 posts at DZone. You can read more from them at their website. View Full User Profile

Using Pen & Paper. Feature Sketches.

12.12.2012
| 2738 views |
  • submit to reddit

This is another blog post in a series about using pen and paper for brainstorming, planning, and designing.

The Single Responsibility Principle is the most important principle of software design. It states that classes should be cohesive, or, in other words, should have only one reason to change. Though it may sound easy in theory, obeying SRP in practice can be difficult, even for experienced developers.

How many times have you tried to refactor out a responsibility from a god class? How many times have you succeeded? It’s hard. Primarily, because of the limitations of the brain. We cannot keep more than 3-4 things in our working memory. This means that understanding the ways in which 30 methods interact with each other is extremely difficult. And that’s when feature sketches can come in handy.

Take a look at this class:

class Account
  attr_reader :number, :balance, :name, :client, :status

  def initialize number, balance, name, client, created_at, status
    @number = number
    @balance = balance
    @name = name
    @client = client
    @status = status
  end

  def withdraw amount, description
    transaction = TransactionFactory.build(@number, -amount, description)
    TransactionRepository.save(transaction)

    @balance -= amount
    AccountRepository.save(self)
  end

  def deposit amount, description
    transaction = TransactionFactory.build(@number, amount, description)
    TransactionRepository.save(transaction)

    @balance += amount
    AccountRepository.save(self)
  end

  def transfer_to destination_account, amount, description
    withdraw amount, description
    destination_account.deposit amount, description
  end

  def transactions
    TransactionRepository.find_all_by_number(@number)
  end

  def can_withdraw? amount
    @status == :open && @balance >= amount
  end

  def close
    if @status != :close
      @status = :close
      AccountRepository.save(self)
    end
  end

  def reopen
    if @status != :open
      @status = :open
      AccountRepository.save(self)
    end
  end
end

Though the Account class is only 50 lines long, and it’s public API consists of only 12 methods, it still takes some time to see what this class does and how it can be refactored.

Let’s see how feature sketches can help us with that.

Step 1. Draw Instance Variables

Start with drawing a circle for each instance variable of the class.

Instance Variables

Step 2. Draw Methods

Next, do the same for each method of the class. To save some space I grouped all the attribute accessors inside the same circle. Then, draw a line from each method to the circles of the variables and methods it accesses or modifies.

Connect Methods

Step 3. Identify Clusters

After you’re done, you should be able to see if there is any clustering in your class.

Clusters

We identified two clusters: the first one is changing the status of an account, and the other one is responsible for working with transactions.

Step 4. Refactor

The last step is to move one of the clusters into a separate class. In our case, the Account class is an information holder and a service provider at the same time. The responsibility for building, finding and saving transactions can be easily refactored out into a service or a DCI context.

Summing Up

Feature sketches can really add to your understanding of the code. In this example, we managed to reduce the number of things to keep in our working memory from twelve down to three by identifying clusters of methods. Which considering the limitations of the brain can have tremendous value.

Read More

I’ve read about Feature Sketches in the book “Working Effectively with Legacy Code” by Michael Feathers. The book is full of great insights, and I highly recommend reading it.


Published at DZone with permission of Victor Savkin, author and DZone MVB. (source)

(Note: Opinions expressed in this article and its replies are the opinions of their respective authors and not those of DZone, Inc.)