Skip to content

Instantly share code, notes, and snippets.

@mikekelly
Created September 23, 2012 12:46
Show Gist options
  • Save mikekelly/3770558 to your computer and use it in GitHub Desktop.
Save mikekelly/3770558 to your computer and use it in GitHub Desktop.
require_relative 'deferrable'
require_relative 'slime'
class WidgetsController
include ControllerSlime
def create
creator = WidgetCreator.new(attributes: params[:widget])
creator.done do |widget|
render nothing: true, status: 201, location: widget_path(widget)
end
creator.fail { |errors| render json: errors, status: 400 }
creator.call
end
end
class WidgetCreator
include Deferrable
attr_reader :attributes
def initialize(args)
@attributes = args.fetch(:attributes)
end
def call
WidgetRepository.save(Widget.new(attributes), self)
end
end
class WidgetRepository
def self.save(widget, listener)
if [true,false].sample
listener.resolve! widget
else
listener.reject! [{donkey: 'does not hover.'}]
end
end
end
5.times { WidgetsController.new.create }
module Deferrable
def done(&block)
done_blocks << block
end
def fail(&block)
fail_blocks << block
end
def resolve!(*args)
done_blocks.each do |block|
block.call(*args)
end
end
def reject!(*args)
fail_blocks.each do |block|
block.call(*args)
end
end
def done_blocks
@_done_blocks ||= []
end
def fail_blocks
@_fail_blocks ||= []
end
end
require 'ostruct'
module ControllerSlime
def widget_path(widget)
"/widgets/#{widget.id}"
end
def render(opts)
puts "#render #{opts.inspect}"
end
def params
{widget: {id: 1, foo: 'bar'}}
end
end
class Widget < OpenStruct; end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment