Skip to content

Instantly share code, notes, and snippets.

@paul
Created November 15, 2011 23:50
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save paul/1368791 to your computer and use it in GitHub Desktop.
Save paul/1368791 to your computer and use it in GitHub Desktop.
class Conductor
include ActiveModel::Conversion
extend ActiveModel::Naming
include ActiveModel::Validations
class_attribute :object_names
def self.presents(*object_names)
self.object_names = object_names
object_names.each do |object_name|
klass = object_name.to_s.tableize.classify.constantize
attr_writer object_name
class_eval <<-CODE, __FILE__, __LINE__
def #{object_name}
@#{object_name} ||= #{klass}.new
end
CODE
end
end
def self.forwards(*methods)
options = methods.pop
to = options[:to]
methods.each do |method|
method_name = [to, method].join('_')
class_eval <<-CODE, __FILE__, __LINE__
def #{method_name}
#{to}.#{method}
end
def #{method_name}=(value)
#{to}.#{method} = value
end
CODE
end
end
def initialize(args = {})
merge(args)
end
def merge(args = {})
args.each do |name, value|
self.send(:"#{name}=", value)
end
end
def objects
self.class.object_names.map { |name| self.send(name) }
end
def objects_and_names
self.class.object_names.inject({}) do |objects, name|
objects[name] = self.send(name)
objects
end
end
def persisted?
objects.map(&:persisted?).all?
end
def save
objects.each(&:save)
end
def run_validations!
super
objects_and_names.each do |name, object|
next if object.valid?
object.errors.each do |attr, error|
local_attribute = [name, attr].join('_')
errors.add(local_attribute, error) if errors[local_attribute].empty?
end
end
errors.empty?
end
end
class RegistrationPresenter < Presenter
presents :account, :user
forwards :name, :to => :account
forwards :email, :password, :to => :user
validates_presence_of :account_name,
:user_email,
:user_password,
:message => "Required"
validates_format_of :user_email,
:with => /\A[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]+\z/,
:message => "Not an Email",
:if => lambda { user_email.present? }
validates_length_of :user_password,
:minimum => 5,
:message => "Too short",
:if => lambda { user_email.present? }
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment