class SchofieldControllerGenerator < Rails::Generator::NamedBase def initialize(runtime_args, runtime_options = {}) super usage if runtime_args.empty? @args = runtime_args.dup base_name = @args.shift assign_names!(base_name) end def manifest record do |m| template_directory = has_parents? ? 'nested' : 'unnested' sco_class = class_name.gsub('Admin::', '').singularize sco_underscored = sco_class.underscore sco_humanized_uc = sco_underscored.humanize sco_underscored_plural = sco_underscored.pluralize sco_titleized_plural = sco_underscored_plural.titleize sco_humanized = sco_humanized_uc.downcase sco_parents = [] if has_parents? options[:parents].each do |parent| sco_parent_class = has_parents? ? parent.classify : '' sco_parent_underscored = sco_parent_class.underscore.downcase sco_parent_underscored_plural = sco_parent_underscored.pluralize sco_parent_titleized_plural = sco_parent_underscored.titleize.pluralize sco_parents << { :class => sco_parent_class, :underscored => sco_parent_underscored, :underscored_plural => sco_parent_underscored_plural, :titleized_plural => sco_parent_titleized_plural, } end end sco_children = [] if has_children? options[:children].each do |child| sco_child_class = has_children? ? child.classify : '' sco_child_underscored = sco_child_class.underscore.downcase sco_child_underscored_plural = sco_child_underscored.pluralize sco_child_titleized_plural = sco_child_underscored.titleize.pluralize sco_child_humanized = sco_child_underscored.humanize.downcase sco_children << { :class => sco_child_class, :underscored => sco_child_underscored, :underscored_plural => sco_child_underscored_plural, :titleized_plural => sco_child_titleized_plural, :humanized => sco_child_humanized } end end assigns = { :sco_underscored => sco_underscored, :sco_underscored_plural => sco_underscored_plural, :sco_class => sco_class, :sco_humanized_uc => sco_humanized_uc, :sco_parents => sco_parents, :sco_titleized_plural => sco_titleized_plural, :sco_humanized => sco_humanized, :non_restful_actions => non_restful_actions, :sco_children => sco_children } # Check for class naming collisions. m.class_collisions class_path, "#{class_name}Controller", "#{class_name}Helper" # Controller, helper, views, and spec directories. m.directory File.join('app/controllers', class_path) m.directory File.join('app/helpers', class_path) m.directory File.join('app/views', class_path, file_name) m.directory File.join('spec/controllers', class_path) m.directory File.join('spec/helpers', class_path) m.directory File.join('spec/views', class_path, file_name) # Controller spec, class, and helper. m.template 'controller_spec.rb', File.join('spec/controllers', class_path, "#{file_name}_controller_spec.rb") m.template 'helper_spec.rb', File.join('spec/helpers', class_path, "#{file_name}_helper_spec.rb") m.template "#{template_directory}/controller.rb", File.join('app/controllers', class_path, "#{file_name}_controller.rb"), :assigns => assigns m.template 'controller:helper.rb', File.join('app/helpers', class_path, "#{file_name}_helper.rb") # Spec and view template for each action. actions.each do |action| m.template 'view_spec.rb', File.join('spec/views', class_path, file_name, "#{action}.haml_spec.rb"), :assigns => { :action => action, :model => file_name } m.template "#{template_directory}/#{action}.rb", File.join('app/views', class_path, file_name, "#{action}.haml"), :assigns => assigns if actions_with_view.include?(action) end if actions.include?('index') || has_parents? m.template 'index_partial.rb', File.join('app/views/shared', "_#{sco_underscored_plural}.haml"), :assigns => assigns end end end def actions_with_view non_restful_actions + %w( index show new edit ) end def restful_actions %w( index show new create edit update destroy sort ) end def non_restful_actions restful_actions - %w( index show new create edit update destroy sort ) end protected def add_options!(opt) opt.separator '' opt.separator 'Options:' opt.on('--parents PARENTS', 'Specify the parent models') { |v| options[:parents] = v if v.present? } opt.on('--children CHILDREN', 'Specify the children models') { |v| options[:children] = v if v.present? } end def has_parents? options[:parents].present? end def has_children? options[:children].present? end def filter_actions array array.map { |item| actions.include?(item) ? ":#{item}" : nil }.compact.join(', ') end def banner "Usage: #{$0} schofield_controller ControllerName [--parents PARENTS --children CHILDREN]" end end