Skip to content
This repository

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP

Generates views for forms provided nested_attributes_for, etc are setup.

branch: master

Fetching latest commit…

Octocat-spinner-32-eaf2f5

Cannot retrieve the latest commit at this time

Octocat-spinner-32 lib
Octocat-spinner-32 test
Octocat-spinner-32 .document
Octocat-spinner-32 .gitignore
Octocat-spinner-32 Gemfile
Octocat-spinner-32 Gemfile.lock
Octocat-spinner-32 LICENSE.txt
Octocat-spinner-32 README.rdoc
Octocat-spinner-32 Rakefile
Octocat-spinner-32 VERSION
Octocat-spinner-32 formgen.gemspec
README.rdoc

formgen

rails g skizmo:form --help

Usage:

rails generate skizmo:form NAME [options]

Options:

[--helpers]       # Indicates when to generate helpers
                  # Default: true
[--javascript]    # Indicates when to generate javascript
                  # Default: true
[--select-boxes]  # Indicates when to generate select boxes
                  # Default: true

Runtime options:

-f, [--force]    # Overwrite files that already exist
-s, [--skip]     # Skip files that already exist
-q, [--quiet]    # Supress status output
-p, [--pretend]  # Run but do not make any changes

Description:

Generates a form per usual but with fields_for for the has_many and belongs_to associations that are 
"accepted_nested_attributes".  If the fields are not accepted nested attributes, then they are 
selectable options, multi-select for has_many and single select for belongs_to.  'has_attached_file' 
will trigger the file_field input and create a multipart form.

Example:

rails generate skizmo:form Foo

With Foo.rb (model like this):
  class Foo < ActiveRecord::Base
    has_many :bars
    belongs_to :baz

    has_many :others
    belongs_to :something

    accepts_nested_attributes_for :bars
    accepts_nested_attributes_for :baz

    has_attached_file :image
  end

This will create:
  public/javascripts/jquery.add_remove_links.js
  app/helpers/add_remove_links_helper.rb
  app/helpers/foo_setup_helper.rb
  app/views/foos/new.html.erb
  app/views/foos/edit.html.erb
  app/views/foos/_form.html.erb
  app/views/foos/_bar_fields.html.erb
  app/views/foos/_baz_fields.html.erb

Static Files

  • public/javascripts/jquery.add_remove_links.js

  • app/helpers/add_remove_links_helper.rb

Generated Files and Examples

Based on Foo example above.

  • app/helpers/foo_setup_helper.rb

  • app/views/foos/new.html.erb

  • app/views/foos/edit.html.erb

  • app/views/foos/_form.html.erb

  • app/views/foos/_bar_fields.html.erb

  • app/views/foos/_baz_fields.html.erb

Examples:

app/helpers/foo_setup_helper.rb

module FooSetupHelper
  def setup_foo(obj)
    obj.build_baz  if obj.baz.blank?
    obj.bars.build if obj.bars.empty?
    return obj
  end

  def build_select_list(assoc, options={})
    name  = options[:name]  || "name"
    scope = options[:scope] || "all"
    begin
      # name and id associations
      assoc.to_s.classify.constantize.send(scope).map{|a| [a.send(name), a.id]}
    rescue
      # use id for text and value
      assoc.to_s.classify.constantize.send(scope).map(&:id)
    end
  end
end

app/views/foos/new.html.erb

<h1>New foo</h1>
<%= render 'form' %>
<%= link_to 'back', :back %>

app/views/foos/edit.html.erb

<h1>Editing foo</h1>
<%= render 'form' %>
<%= link_to 'back', :back %>

app/views/foos/_form.html.erb

<%= form_for setup_foo(@foo), :html => { :multipart => true } do |f| %>
  <% if @foo.errors.any? %>
    <div id="errorExplanation">
      <h2><%= pluralize(@foo.errors.count, "error") %> prohibited this foo from being saved:</h2>
      <ul>
        <% @foo.errors.full_messages.each do |msg| %>
          <li><%= msg %></li>
        <% end %>
      </ul>
    </div>
  <% end %>
  <div class="field">
    <%= f.label :name %>
    <%= f.text_field :name %>
  </div>
  <div class="field">
    <%= f.label :description %>
    <%= f.text_area :description %>
  </div>
  <div class="field">
    <%= f.label :image %>
    <%= f.file_field :image %>
  </div>
  <div class="field">
    <%= f.label :other_ids, "Others" %>
    <%= f.select :other_ids, build_select_list(:others), {:prompt => "Please select"}, {:multiple => true, :size => 4} %>
  </div>
  <div class="field">
    <%= f.label :something_id, "Something" %>
    <%= f.select :something_id, build_select_list(:something), {:prompt => "Please select one"} %>
  </div>
  <%= f.fields_for :baz do |nf| %>
    <%= render 'baz_fields', :f => nf %>
  <% end %>
  <%= f.fields_for :bars do |nf| %>
    <%= render 'bar_fields', :f => nf %>
  <% end %>
  <%= link_to_add_fields "Add bar", f, :bars %>
  <%= f.submit "Save" %>
<% end %>
<%= content_for :head do %>
  <%= javascript_include_tag 'jquery.add_remove_links.js' %>
<% end %>

app/views/foos/_bar_fields.html.erb

<div class="fields">
  <div class="field">
    <%= f.label :name %>
    <%= f.text_field :name %>
  </div>
  <div class="field">
    <%= f.label :bar %>
    <%= f.text_field :bar %>
  </div>
  <%= link_to_remove_fields "remove", f %>
</div>

app/views/foos/_baz_fields.html.erb

<div class="fields">
  <div class="field">
    <%= f.label :name %>
    <%= f.text_field :name %>
  </div>
  <div class="field">
    <%= f.label :image %>
    <%= f.file_field :image %>
  </div>
</div>

FAQ

  • I'm getting this error: “undefined method `setup_something' for …”:

    Make sure the generated helper is being loaded - restart your rails server.

  • I want haml templates instead of erb:

    Done - just include this gem github.com/indirect/haml-rails

Gotchas

  • Only does single level nesting at this point. For example, if the Bar or Baz class had accepts_nested_attributes_for :thing, it would not generate those partials and form elements. Yet. This is the only thing on my TODO list before I'd call it a solid 1.0.0.

  • You need to use yield :head somewhere in your layout to take advantage of the jQuery that is loaded in a content_for :head to supply add and remove jQuery.

Contributing to formgen

  • Check out the latest master to make sure the feature hasn't been implemented or the bug hasn't been fixed yet

  • Check out the issue tracker to make sure someone already hasn't requested it and/or contributed it

  • Fork the project

  • Start a feature/bugfix branch

  • Commit and push until you are happy with your contribution

  • Make sure to add tests for it. This is important so I don't break it in a future version unintentionally.

  • Please try not to mess with the Rakefile, version, or history. If you want to have your own version, or is otherwise necessary, that is fine, but please isolate to its own commit so I can cherry-pick around it.

Copyright

Copyright © 2011 Pullmonkey. See LICENSE.txt for further details.

Something went wrong with that request. Please try again.