Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Dinosaurs, Lasers, and the Decorator Pattern

mileszs
February 09, 2012

Dinosaurs, Lasers, and the Decorator Pattern

Quick overview of the decorator pattern, and the implementation of that pattern in Rails in the form of the gem Draper. Also, dinosaurs and lasers.

mileszs

February 09, 2012
Tweet

Other Decks in Programming

Transcript

  1. Wikipedia says: “In object-oriented programming, the decorator pattern is a

    design pattern that allows behaviour to be added to an existing object dynamically.”
  2. 1 require File.join(Rails.root, 'lib', 'slug') 2 class Job < ActiveRecord::Base

    3 include IndyHackers::Slug 4 5 has_many :job_views 6 has_many :viewers, :through => :job_views 7 belongs_to :user 8 9 after_update :notify_if_published 10 11 scope :published, lambda { 12 where("jobs.published_at IS NOT NULL AND jobs.published_at <= ?", Time.zone.now) 13 } 14 15 def notify_if_published 16 if published_at_changed? && published_at.present? && published_at <= Time.now 17 SystemMailer.job_post_published(self.user, self).deliver 18 else 19 Rails.logger.info "OMG WTF BBQ" 20 end 21 end 22 end
  3. 1 require File.join(Rails.root, 'lib', 'slug') 2 class Job < ActiveRecord::Base

    3 include IndyHackers::Slug 4 5 has_many :job_views 6 has_many :viewers, :through => :job_views 7 belongs_to :user 8 9 after_update :notify_if_published 10 11 # ... 12 13 def pretty_job_date 14 published_at.strftime("%B %d %h:%m%P") 15 end 16 17 def viewers_total 18 "#{viewers.size} People Have Viewed This Post" 19 end 20 end
  4. 1 .grid_10.prefix_1 2 %section.readable 3 %article.job#single-job 4 %h1= @job.title 5

    %p= @job.pretty_published_at 6 %p= @job.viewers_total 7 .job-description 8 = MARKDOWN.render(@job.description).html_safe
  5. 1 class JobDecorator < ApplicationDecorator 2 decorates :job 3 4

    def published_at 5 # 'h' exposes Rails helpers w/i your decorator 6 # 'model' exposes the actual object you're decorating 7 h.l(model.published_at, :format => :murican_time) 8 end 9 10 def total_viewers 11 "#{model.viewers.size} People Have Viewed This Post" 12 end 13 14 def description_html 15 MARKDOWN.render(model.description).html_safe 16 end 17 end
  6. 1 .grid_10.prefix_1 2 %section.readable 3 %article.job#single-job 4 %h1= @job.title 5

    %p= @job.published_at 6 %p= @job.total_viewers 7 .job-description 8 = @job.description_html
  7. 1 2 class JobsController < ApplicationController 3 def index 4

    @jobs = JobDecorator.decorate(Job.published) 5 end 6 7 def show 8 @job = JobDecorator.find(params[:id]) 9 10 # or 11 # @job = Job.find(params[:id] 12 # @job = JobDecorator.new(@job) 13 end 14 end