Your SlideShare is downloading. ×

Talking to strangers causes train wrecks


Published on

I give this as a lightning talk at philly.rb on 1/15/2013. It's a discussion of the challenges of applying the Law of Demeter to Rails programming.

I give this as a lightning talk at philly.rb on 1/15/2013. It's a discussion of the challenges of applying the Law of Demeter to Rails programming.

  • Be the first to comment

  • Be the first to like this

No Downloads
Total Views
On Slideshare
From Embeds
Number of Embeds
Embeds 0
No embeds

Report content
Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

No notes for slide


  • 1. Talking to strangers causes train wrecks Mike Toppa, @mtoppa January 15, 2013Wednesday, January 16, 13
  • 2. Goal: unpack this quote “Mockist testers do talk more about avoiding train wrecks - method chains of style getThis().getThat().getTheOther(). Avoiding method chains is also known as following the Law of Demeter. While method chains are a smell, the opposite problem of middle men objects bloated with forwarding methods is also a smell. (Ive always felt Id be more comfortable with the Law of Demeter if it were called the Suggestion of Demeter.)” Martin Fowler, 2004 Mocks aren’t StubsWednesday, January 16, 13
  • 3. Steps to understanding ✤ What is the Law of Demeter? ✤ How does it pertain to traditional OO vs. ActiveRecord? ✤ What are the implications for testing? ✤ What are the alternatives to train wrecks?Wednesday, January 16, 13
  • 4. The Law of Demeter ✤ AKA Principle of Least Knowledge, AKA “Don’t talk to strangers” ✤ Only Talk To Friends ✤ Objects Closely Related To The Class ✤ Reduces Dependencies ✤ Benefits: ✤ Maintainable Code ✤ Reusable Code ✤ Easy To Understand Code From Don’t Be STUPID, grasp SOLIDWednesday, January 16, 13
  • 5. A helpful analogy.... ✤ You can play with yourself. ✤ You can play with your own toys (but you can’t take them apart), ✤ You can play with toys that were given to you. ✤ And you can play with toys you’ve made yourself. From Peter Van Rooijen, WikiWikiWednesday, January 16, 13
  • 6. Traditional OO approach: dependency inversion <<interface>> Button SwitchableDevice + poll() +turnOn() +turnOff() class Button { private $switchableDevice; public function __construct(SwitchableDevice $switchableDevice) { Lamp $this->switchableDevice = $switchableDevice; } public function poll() { if (/* some condition */) { $this->switchableDevice->turnOn(); } } From Agile Software DevelopmentWednesday, January 16, 13
  • 7. Typical Rails approach: Method chaining ✤ ActiveRecord makes it easy, but at the cost of lost abstraction: ✤ Button class: has_one :lamp ✤ Lamp class: belongs_to :button ✤ button.lamp.turn_on ✤ Which makes it easy to end up with a train wreck... ✤ person.timers.first.button.lamp.turn_onWednesday, January 16, 13
  • 8. Testing with train wrecks ✤ Mocks become impractical ✤ Factories may help, but FactoryGirl can only go two levels deep: @weed = FactoryGirl.create(:politician, :with_campaign, name: M. Teresa Paiva-Weed) ✤ You will probably need to rely on fixtures or seeding with test data ✤ Bottom line: you will have to rely on integration testing, not unit testingWednesday, January 16, 13
  • 9. Reducing the number of dots I Use a has_many :through relationship class Physician < ActiveRecord::Base has_many :appointments has_many :patients, :through => :appointments endWednesday, January 16, 13
  • 10. Reducing the number of dots II Use delegation class User delegate :name, :to => :department, :prefix => true, :allow_nil => true # ... end .... def user_info(user) "Name: #{}. Dept: #{user.department_name}" end From Demeter: It’s not just a good idea. It’s the law.Wednesday, January 16, 13
  • 11. Reducing the number of dots III ✤ Use POROs (plain old ruby objects) for business logic. This means ✤ Your Rails models will be skinny ✤ You can use whatever principles and patterns you want ✤ For me, this is where the conundrum lies: ✤ The speed and power of “the Rails way” vs. ✤ The adaptability (and testability) of traditional OO patternsWednesday, January 16, 13