I am working on configuring the apartment gem for my rails app to give users the functionality to create subdomains. I have a nested form and when attempting to access "accounts/new" I am getting the following error:
no implicit conversion of Symbol into Integer in view forms
accounts/new.html.erb
<div>
</div>
<h2>Create an Account</h2>
<%= form_for #account do |f| %>
<%= f.fields_for :owner do |o| %>
<%= form_for o, :email do %>
<%= o.text_field :email, class: 'form-control' %>
<% end %>
<%= form_for o, :password do %>
<%= o.password_field :password, class: 'form-control' %>
<% end %>
<%= form_for o, :password_confirmation do %>
<%= o.password_field :password_confirmation, class: 'form-control' %>
<% end %>
<% end %>
<%= form_for f, :subdomain do %>
<div class="input-group">
<%= f.text_field :subdomain, class: 'form-control' %>
<span class="input-group-addon">.scrumteam.com</span>
</div>
<% end %>
<%= f.submit class: 'btn btn-primary' %>
<% end %>
</div>
</div>
accounts_controller.rb
private
def account_params
params.require(:account).permit(:subdomain, :owner_attributes => [:email, :password, :password_confirmation])
end
You are nesting multiple forms into each other which is not supported in HTML:
See this question for more details: Can you nest html forms?
These form_for lines look invalid in particular:
<%= form_for o, :field_name do %>
Here, o is a special FormBuilder object which should not be fed to form_for. Try this instead:
<%= f.fields_for :owner do |o| %>
<%= o.fields_for :email do %>
Unlike form_for, it is possible to nest fields_for blocks.
Not sure if this is your route problem, but form_for creates an actual form tag in html. You only need (and should have) 1, the fields_for allows you to switch the form helpers to a different object, but you don't need to call form_for again within it. If you're just trying to group your form fields, you can just add some divs and/or labels.
Related
a. I create a migration
def change
add_column :tournament_matches, :team_a_sets, :text
add_column :tournament_matches, :team_b_sets, :text
end
b. I added Serialize in model
class TournamentMatch < ApplicationRecord
serialize :team_a_sets, Array
serialize :team_b_sets, Array
end
c. I allow strong params in my controller
def tennis_params
params.require(:tournament_match).permit(:match_result, team_a_sets: [], team_b_sets: [])
end
d. my form looks like this:
<%= form_with model: #tournament_match, url: update_tennis_game_result_tournament_match_path(#tournament_match), method: :patch do |f| %>
<%= f.label :team_a, 'Team A' %>
<%= f.number_field 'team_a_sets[]' %>
<%= f.number_field 'team_a_sets[]' %>
<%= f.number_field 'team_a_sets[]' %>
<%= f.number_field 'team_a_sets[]' %>
<%= f.number_field 'team_a_sets[]' %><br>
<%= f.label :team_a, 'Team B' %>
<%= f.number_field 'team_b_sets[]' %>
<%= f.number_field 'team_b_sets[]' %>
<%= f.number_field 'team_b_sets[]' %>
<%= f.number_field 'team_b_sets[]' %>
<%= f.number_field 'team_b_sets[]' %><br>
<%= f.submit 'Submit', class: 'btn btn-primary btn-block' %>
<% end %>
e. my controller looks like this
def update_tennis_game_result
tournament_match = TournamentMatch.find(params[:id])
tournament_match.update_attributes(tennis_params)
redirect_to tournament_path(tournament_match.tournament.id)
end
But when I am submitting my form, I am getting empty array for team_a_sets[] and team_b_sets[]. What I am doing wrong ? I want to store games results in team_a_sets and team_b_sets as array.
My params after submitting my form looks like this:
Parameters: {"authenticity_token"=>"Rd/3zOIv0Ldmq/qxlIDPcYzcAuhPmz20JYUpHedeeQSwtp4gf8RhYfXcLdhrlVdDQxGjHtCK6Cq0FB6FNWtdPQ==", "tournament_match"=>{"match_result"=>"home_win", "team_a_sets"=>[], "team_b_sets"=>[]}, "commit"=>"Submit", "id"=>"296b8505-c116-4e08-a48a-53366eac93b0"}
It looks like form_helper check the suffix [] to detect multiple fields.
But your form input
<%= f.number_field 'team_a_sets[]' %>
will generate html_tag like this
input type="number" name="tournament_match[team_a_sets[]]" id="tournament_match_team_a_sets[]"
in which the name hasn't the suffix [].
you could try this instead:
<%= form.number_field 'team_a_sets', multiple: true %>
the html_tag is generated in this case
input multiple="multiple" type="number" name="tournament_match[team_a_sets][]" id="tournament_match_team_a_sets"
in which the html_name has suffix [].
I guess I'm a little confused on how fields_for works. I have an action with this:
3.times { #submitted_quiz.submitted_answers.build }
if I write a form_for like this in the associated view:
<%= form_for(#submitted_quiz) do |f| %>
<%= f.hidden_field :quiz_id, :value => #quiz.id %>
<%= f.hidden_field :name, :value => #quiz.name %>
<%= f.fields_for (:submitted_answers) do |ff| %>
<%= ff.label :content, "Answer" %><br />
<%= ff.text_area :content, :rows => 3 %>
<% end %>
<%= f.submit %>
<% end %>
how does fields_for know to run three times?
Rails will simply check how many submitted_answers your submitted_quiz has and generate appropriate number of fields ( one for each answer obviously ).
I have the following simple rails page:
<h1> New User </h1>
<%= form_for :user, url:users_path do |f| %>
<p>
<%= f.label :email %>
<%= f.text_field :email %>
</p>
<p>
<%= f.label :password %>
<%= f.text_field :password %>
</p>
<%= f.submit %>
<% end %>
The create action gets executed and I want to access the :email attribute.
def create
render text: params[:email].inspect
end
The above always displays nil.
form_for :user will place all parameters beneath a :user key
render text: params[:user][:email].inspect
I have a model Person with the following attributes:
:name, :state, :age, :town
Let's say I want to be able to edit all of the attributes except for :name from that Person's edit view. Is there a "rails" way to do this, and if so what would I write without looping through each attribute and creating a form?
Right now, I've got something like this:
<%= form_for #person do |person_form| %>
<%= person_form.fields_for :age do |age_form| %>
<%= age_form.text_field :age %>
<% end %>
<% end %>
And I would do that for each attribute.
It would be just a standard form since the object you're wrapping the form around has all of the attributes.
<%= form_for #person do |f| %>
<%= f.text_field :state %>
<%= f.text_field :age %>
<%= f.text_field :town %>
<%= f.submit %>
<% end %>
Of course, you can add labels and whatever else you need to the form.
Is it possible to specify html attributes while using the form_for helper methods?
For example:
<% form_for #user do |f| %>
<%= f.label :username%>
<%= f.text_field :username %>
<%= f.submit "Signn Up" %>
<% end %>
How would I go about specifying the class for the label? Is it possible, or do I have to resort to label()?
On mostly helpers, the last arg is a hash of html options for the element.
<%= f.label :username, "Username", :class => "class" %>