Rails Losing Params during Post Method - ruby-on-rails

I have a form where I don't know how many text_fields there are going to be. For each row in the table/form, there is the basename of the file, and a hidden field next to it so it is passed in, along with the 2 text fields, the params[:lots[key][lot_number][:low_range][:high_range].
Once I get to the Controller I only have 2 - 3 of the original 8 sets of fields that where produced. I'm not sure why these other fields are being left behind.
I tried doing it with 15+ fields and it still only gets 5-7 of the lots each time.
The information I get is correct and formated correctly. I'm just always missing over half of the lots that are rendered in the #video_filenames loop
View:
<%= form_tag mass_create_from_media_admin_event_lots_path(#event), :method => :post do %>
<table class='list'>
<th>Lots</th>
<th>Sub Lot Creation</th>
<% if !params[:videos] || params[:videos] == '1' %>
<% #video_filenames.reject(&:blank?).uniq.each do |filename| %>
<% basename = File.basename(filename, '.*') %>
<% unique_key = Time.now.to_f %>
<tr>
<td><%= basename %><%= hidden_field_tag "lots[#{unique_key}][lot_number]", basename %></td>
<td><%= text_field_tag "lots[#{unique_key}][low_range]" %> <%= text_field_tag "lots[#{unique_key}][high_range]" %></td>
</tr>
<% end %>
<% end %>
</table>
<%= submit_tag "Create Lots" %>
<% end %>
Controller:
def mass_create_from_media
#event = Event.find(params[:event_id])
lots = params[:lots]
abort(params.to_s)
errors = []
lots.each do |key , lot|
if #event.lots.where(:number => lot[:lot_number]).empty?
new_lot = #event.lots.new(:number => lot[:lot_number], :start_at => Time.now, :end_at => Time.now + 1.hour)
if !new_lot.save
errors << new_lot.errors.full_messages
else
if lot[:low_range].present? && lot[:high_range].present?
index = lot[:low_range]
while lot[:high_range].to_i >= index.to_i
sub_lot = #event.lots.new(:number => lot[:lot_number] + '-' + index.to_s, :start_at => Time.now, :end_at => Time.now + 1.hour)
index = index.to_i + 1
sub_lot.save
end
end
end
end
end
if errors.present?
flash[:error] = "Errors creating lots: #{errors.join(', ')}"
else
flash[:success] = "Lots successfully created"
end
redirect_to mass_new_admin_event_lots_path(#event)
end
HTML Output:
<input id="lots_1369421745.947125_lot_number" name="lots[1369421745.947125][lot_number]" type="hidden" value="101z">
<input id="lots_1369421745.947125_lot_number" name="lots[1369421745.947125][lot_number]" type="hidden" value="115z">
<input id="lots_1369421745.947125_lot_number" name="lots[1369421745.947125][lot_number]" type="hidden" value="161z">
<input id="lots_1369421745.948125_lot_number" name="lots[1369421745.948125][lot_number]" type="hidden" value="20z">
<input id="lots_1369421745.948125_lot_number" name="lots[1369421745.948125][lot_number]" type="hidden" value="20z">
<input id="lots_1369421745.948125_lot_number" name="lots[1369421745.948125][lot_number]" type="hidden" value="47z">
<input id="lots_1369421745.948125_lot_number" name="lots[1369421745.948125][lot_number]" type="hidden" value="87z">
<input id="lots_1369421745.948125_lot_number" name="lots[1369421745.948125][lot_number]" type="hidden" value="rock_on">
Text Inputs:
<input id="lots_1369421745.948125_high_range" name="lots[1369421745.948125][high_range]" type="text">
<input id="lots_1369421745.948125_low_range" name="lots[1369421745.948125][low_range]" type="text">

Try this
<% #video_filenames.reject(&:blank?).uniq.each_with_index do |filename, index| %>
<% basename = File.basename(filename, '.*') %>
<tr>
<td><%= basename %><%= hidden_field_tag "lots[#{index}][lot_number]", basename %></td>
<td><%= text_field_tag "lots[#{index}][low_range]" %> <%= text_field_tag "lots[#{index}][high_range]" %></td>
</tr>
<% end %>
<% end %>

The problem is <% unique_key = Time.now.to_f %> is not generating uniq keys. As you can see in the html, keys 1369421745.947125 and 1369421745.948125 are repeated.
So, you have to change your "algorithm" to generate uniq keys.

I changed <% unique_key = Time.now.to_f %> to <% unique_key = SecureRandom.urlsafe_base64 %>

Related

Two submission forms with form-tag on same page in rails

I have a weekly time entry form currently. How can i have another time entry form on the same page ? and these two forms need be submitted separately as different records. Any help would be appreciated .
Here is my code:-
show_weeks.html.erb
<div class="table-responisve>
<% if #dates != nil %>
<table class="table-bordered">
<thead>
<tr>
<% #dates.each do |date| %>
<th><%=date.to_s+","+date.strftime("%A").to_s %> </th>
<% end %>
</thead>
<tbody>
<tr>
<% #dates.each do |date| %>
<% if #time_entry %>
<td><%= text_field_tag "#{date}", #time_entry.hour_per_day["#{date}"], class: "dates" %></td>
<% else %>
<%if date < Date.today %>
<td> <%= text_field_tag "#{date}", "", class: "dates" %> </td>
<%else %>
<td><%= text_field_tag "#{date}", "", class: "dates" if date == Date.today && Time.now.strftime("%H").to_i >= 10 %> </td>
<% end %>
<% end %>
<% end %>
</tr>
<tr>
<% if #time_entry %>
<td colspan="2"> Please Enter your Comment </td>
<td colspan="5">
<% #time_entry.comments.each do |c| %>
<p><%= text_field_tag "Comment", c.message %> </p>
<% end %>
</td>
<%else%>
<td colspan="2"> Please Enter your Comment </td>
<td colspan="5"><%= text_field_tag "Comment", "" %>
</td>
<%end%>
</tr>
</tbody>
</table>
</div>
<button type="button" class="btn btn-primary"
id="save_entries">Submit</button>
<%= form_tag save_time_entries_path, method: 'post',
id:"save_time_entries" do %>
<%= hidden_field_tag "start_date", #dates.first%>
<%= hidden_field_tag "end_date", #dates.last%>
<%= hidden_field_tag "total_hours", "" %>
<%= hidden_field_tag "project_id", #project.id %>
<%= hidden_field_tag "time_entry", "" %>
<%= hidden_field_tag "message", "" %>
<% if #time_entry%>
<%= hidden_field_tag "time_entry_detail_id", #time_entry.id %>
<% end %>
<% end %>
<script>
$("#save_entries").click(function(){
var time_entry = []
var hours = 0;
var message = document.getElementById("Comment").value;
$('.dates').each(function() {
hours += Number($(this).val());
if ($(this).val() == 0)
{
time_entry.push($(this).attr('name'),0)
}else{
time_entry.push($(this).attr('name'),$(this).val())
}
});
if (hours > 60) {
alert("Total Hours Should be equal to 60");
return false;
}
else {
$("#message").val(message);
$("#time_entry").val(time_entry);
$("#total_hours").val(hours);
$("#save_time_entries").submit();
}
})
</script>
<%end%>
you can create 2 different forms with form_for, it shouldn't be a problem
I figure out solution. Using of two submission forms on same page is bad idea. So I have create previous weeks records by using after create call back and i given default values for TimeEntryDetail. Here it creates all weeks records in background. Suppose if you skipped for 6 weeks , it'll create 6 empty records in background. Here is my working code
Modal.rb
after_create :chceck_time
def check_time
#project_mem_check= ProjectMember.where(project_id: project, member_id: user).first.created_at
#present week dates coming here |
#time_entry_check = TimeEntryDetail.where(project_id: project, user_id: user).first.created_at
if #time_entry_check.nil?
#time_entry_check=#project_mem_check
end
#last_week_start=Date.today.beginning_of_week
#last_week_end =Date.today.end_of_week
#cheking project member creation shall be less than time entry creation of that project.
if #project_mem_check <= #time_entry_check
#time_check_first=TimeEntryDetail.where(project_id: project, user_id: user).pluck(:start_date).first.to_date
#time_check_last =TimeEntryDetail.where(project_id: project, user_id: user).pluck(:start_date).last.to_date
#check first entry == last time entry
if #time_check_first==#time_check_last
pm=ProjectMember.where(project_id: project, member_id: user).first.created_at.to_date
tm=Date.today.to_date
unfilled_weeks= ((tm-pm)/7).to_i+1
unfilled_weeks.times {
#last_week_start= #last_week_start-7
#last_week_end = #last_week_end-7
#call_back_entry=TimeEntryDetail.create(start_date: (#last_week_start).to_date, end_date: (#last_week_end).to_date,
project_id: project.id, user_id: user.id, hours: 0, aasm_state: "pending", hour_per_day: "" )
#call_back_entry.comments << Comment.create(message: "Please fill the timesheet ")
}
else
#Already this user have time entries and create empty records from where he stopped.
pm=created_at.to_date #--.present time entry is coming
tm=Date.today.to_date
unfilled_weeks= ((tm-pm)/7).to_i+1
unfilled_weeks.times{
#last_week_start= #last_week_start-7
#last_week_end = #last_week_end-7
#call_back_entry=TimeEntryDetail.create(start_date: (#last_week_start).to_date, end_date: (#last_week_end).to_date,
project_id: project.id, user_id: user.id, hours: 0, aasm_state: "submitted", hour_per_day: "" )
#call_back_entry.comments << Comment.create(message: "Not yet filled this week ")
}
end
end
end

Cant get the Edit function Working

I have two models Employee and Overtime Definition The Associations are set like this
Employee
class Employee < ActiveRecord::Base
has_many :overtime_definitions
Overtime Definition
class OvertimeDefinition < ActiveRecord::Base
belongs_to :employee
I created an Overtime definition for an employee and it all looks fine.However I'm having trouble with editing the same for an employee.
overtime_definitions__controller:
def new
#flag = params[:flag]
#employee = Employee.find(params[:id])
#overtime = OvertimeDefinition.new
end
def create
#employee = Employee.find(params[:overtime_definition][:employee_id])
#overtime = OvertimeDefinition.new(params[:overtime_definition])
if (params[:half_day_extra_duty_hours][:hour].to_s !="" || params[:half_day_extra_duty_hours][:minute].to_s !="")
#overtime.half_day_extra_duty_hours = params[:half_day_extra_duty_hours][:hour].to_s + ":" + params[:half_day_extra_duty_hours][:minute].to_s + ":" + "00"
else
#overtime.half_day_extra_duty_hours = nil
end
if (params[:full_day_extra_duty_hours][:hour].to_s !="" || params[:full_day_extra_duty_hours][:minute].to_s !="")
#overtime.full_day_extra_duty_hours = params[:full_day_extra_duty_hours][:hour].to_s + ":" + params[:full_day_extra_duty_hours][:minute].to_s + ":" + "00"
else
#overtime.full_day_extra_duty_hours = nil
end
if #overtime.save
flash[:notice] = "Overtime Successfully Created for #{#employee.name}"
redirect_to :action => 'search_overtime'
end
end
def edit
#flag = params[:flag]
#overtime = OvertimeDefinition.find(params[:id][:employee_id])
#employee = Employee.find(params[:id])
end
def update
#employee = Employee.find(params[:id])
#overtime = OvertimeDefinition.find(params[:id])
if #overtime.update_attributes(params[:overtime_definition])
flash[:notice] = "Overtime Successfully Updated for #{#employee.name}"
redirect_to :action => 'search_overtime'
else
render :action => 'edit',:flag=>params[:flag]
end
end
Tried with these in the edit method
#overtime = OvertimeDefinition.find(params[:id][:employee_id])
#gives me can't convert Symbol into Integer error.
#overtime = OvertimeDefinition.find(params[:id])
#gives me Couldn't find OvertimeDefinition with ID=1353 error.Actually 1353 is the id of that employee.
3.#overtime = OvertimeDefinition.find(params[:employee_id])
#gives me couldn't find OvertimeDefinition without an ID error.
My _search_overtime_employee_list having these links for new and edit actions
<%=link_to "Calculation" ,:action => "new",:id=>employee.id, :flag=>"Calculation" %>
<%= link_to "Re-Calculate",:action => "edit",:id=>employee.id,:flag=>"Re-Calculate" %>
new.rhtml
<%= form_tag :action => 'create' do %>
<%= render :partial =>'form'%>
<center>
<%= submit_tag "Save",:onclick=>"return validate()",:class=>"buttons"%>
</center>
<% end %>
<%= link_to "Back" ,:action => "search_overtime" %>
edit.rhtml
<%= form_tag :action => 'update', :id=>#employee.id,:flag=> params[:flag],:value=>params[:id] %>
<%= render :partial =>'form'%>
<center>
<%= submit_tag "Update",:onclick=>"return validate()",:class=>"buttons"%>
</center>
<%= link_to "Back" ,:action => "search_overtime" %>
_form.rhtml
Employee Details
<table cellspacing="5">
<tr>
<td><b>Employee Code</b></td>
<%= hidden_field 'overtime_definition','employee_id',:value=>params[:id] %>
<td><%= #employee.employeeid %></td>
<td><b>Employee Name</b></td>
<td><%= #employee.personnel.display_full_name %></td>
</tr>
<tr>
<td><b>Department</b></td>
<td><%= #employee.department ? #employee.department.name : "" %></td>
<td><b>Designation</b></td>
<td><%= #employee.designation ? #employee.designation.name : "" %></td>
<td><b>Location</b></td>
<td><%= #employee.location.name%></td>
</tr>
</table>
</br>
<fieldset>
<table cellspacing="5">
<%= form_for :overtime_definition, :builder => LabelFormBuilder do |od| %>
<tr>
<td>
<label for="half_day_extra_duty_hours">
Half Day Extra Duty Hours
</label>
</td>
<td class ="datefamily">
<%= select_time(#overtime.half_day_extra_duty_hours, {:include_blank => true, :time_separator => ":",:prefix => "half_day_extra_duty_hours"})%>
</td>
</tr>
<tr>
<td>
<label for="full_day_extra_duty_hours">
Full Day Extra Duty Hours
</label>
</td>
<td class ="datefamily">
<%= select_time(#overtime.full_day_extra_duty_hours, {:include_blank => true, :time_separator => ":",:prefix => "full_day_extra_duty_hours"})%>
</td>
</tr>
<tr>
<%= od.sr_check_box :is_salary_basis, {}, true, false, :label => "Is Salary Basis"%>
</tr>
<tr>
<%= od.sr_check_box :is_fixed_amount, {}, true, false, :label => "Is Fixed Amount"%>
<td colspan="2" id="ov_hm" style="display: none">
Half Day Amount
<%= od.text_field :half_day_amount, :onkeypress => "return numbersonly(event)", :style => "width:40px" %>
</td>
<td colspan="2" id="ov_fm" style="display: none">
Full Day Amount
<%= od.text_field :full_day_amount, :onkeypress => "return numbersonly(event)", :style => "width:40px" %>
</td>
</tr>
<%end%>
</table>
I just lost out here completely in getting that edit action work.Any help is greatly appreciated!
Your current edit link is:
<%= link_to "Re-Calculate",:action => "edit",:id=>employee.id,:flag=>"Re-Calculate" %>
In your edit action:
#overtime = OvertimeDefinition.find(params[:id][:employee_id]) ## gives me can't convert Symbol into Integer error.
As per the edit link, you are directly passing :id in query params which you can access as params[:id]. There is no params[:id][:employee_id] in your params hash so when you say params[:id][:employee_id] Ruby tries to convert :employee_id to an integer which is a symbol. Hence, the error.
I think you should be passing id of OvertimeDefinition record in :id from your link. And access it as
#overtime = OvertimeDefinition.find(params[:id])
in the Controller's action.
#overtime = OvertimeDefinition.find(params[:id]) ## gives me Couldn't
find OvertimeDefinition with ID=1353 error.Actually 1353 is the id of
that employee.
This is because you are passing employee id in params[:id] so obviously this will not work. You need to pass OvertimeDefinition id here.
#overtime = OvertimeDefinition.find(params[:employee_id]) ## gives me
couldn't find OvertimeDefinition without an ID error.
You are not passing any :employee_id in query params within edit link. So, params[:employee_id] will be nil and find method fails because you didn't pass any id to it.
Solution :
Update your edit link as below:
<%= link_to "Re-Calculate",:action => "edit",:id=> #overtimedefinition.id , :employee_id => employee.id,:flag=>"Re-Calculate" %>
Replace #overtimedefinition.id with appropriate id of OvertimeDefinition record. As you have not shared the code, I don't know the name of OvertimeDefinition variable.
Update your edit action as:
def edit
#flag = params[:flag]
#overtime = OvertimeDefinition.find(params[:id])
#employee = Employee.find(params[:employee_id])
end

getting checkbox value in ruby on rails

I have a checkbox below in a view page:
<table>
<tr>
<td>
<% #user_profession.each do |p| %>
<% if !p.Designation.blank? and p.Private? == "1" %>
<%= check_box(:ChkBx_Profession, {:id => "ChkBx_Profession",:value => "Profession"},true) %>
<%= label(:lb_Profession, "Profession") %>
<% else %>
<%= check_box(:ChkBx_Profession,{:id => "ChkBx_Profession",:value => "Profession"}) %>
<%= label(:lb_Profession, "Profession") %>
<% end %>
<% end %>
</td>
</tr>
</table>
Below is my controller page
if params[:ChkBx_Profession] == "1"
#blah = params[:ChkBx_Profession]
#publicprofession = params[:ChkBx_Profession]
Profession.delete_all(:UserID => current_user.id)
if !params[:tf_designation].blank?
#desig = params[:tf_designation]
#comp = params[:tf_company]
#fromdesigcom = params[:tf_fromdesignation]
#todesigcom = params[:tf_todesignation]
#public_profession = #publicprofession
#Profession = Profession.new( :UserID => current_user.id, :Designation => #desig, :Company => #comp, :Job_From => #fromdesigcom, :Job_To => #todesigcom, :Private? => #publicprofession )
#Profession.save
end
end
and I want to get the checkbox value means if checkbox is checked it gets me 1 and if checkbox is unchecked it gets me 0 but its get like this {"{:id=>\"ChkBx_Profession\", :value=>\"Profession\"}"=>"1"}. Kindly help me waiting for your reply.
Thanks
The second attribute on an check_box is the :value attribute. Try putting empty double quotes between the chec_box name AND the options:
<%= check_box(:YourCheckName, "",{Your Options}) %>

Pagination not working correctly in rails

I am trying to use will_paginate for a list of items I want to display.
There is a form with drop down selections to fetch objects by status.
This is my controller
def list
#person = Person.find_by_id(session[:person_id])
params[:status] = params[:redirect_status] if params.has_key?('redirect_status')
#statuses = Peptide.statuses
#status = 'Not Ordered'
#status = params[:status] if params[:status] != nil || params[:status] == ''
#peptides = Peptide.find(:all, :conditions => ['status = ?', #status]).paginate(:per_page => 30, :page => params[:page])
if Peptide.count.zero?
flash[:notice] = "There are not any peptides entered"
redirect_to :action => 'new'
end#if zero
end
This is in the view
<form action="/peptide/create_spreadsheet_of_not_ordered" enctype="multipart/form-data" method="post">
<table class="sortable" cellpading="5" cellspacing="2" width="100">
<tr class= "header-line">
<th>SS</th>
<th>Status</th>
<th>Peptide</th>
<th>Gene</th>
<th>Submitter</th>
<th>Created</th>
<th>Updated</th>
<th>Sequence</th>
<th>Modification</th>
<th>Vendor</th>
</tr>
<% for #peptide in #peptides.reverse %>
<tr valign = "top" class= "<%= cycle('color_one', 'color_two') %>">
<!--an error here during development likely indicates that the people table has not be repopulated or
that no submitter primer is present for a primer-->
<td sorttable_customkey = 0 > <%=check_box_tag "box[]", #peptide.id %>
<td><%= #peptide.status%></td>
<td class><%= link_to #peptide.name, :action => :report, :id => #peptide.id %></td>
<td><%= gene_links(#peptide.genes) rescue 'Error'%></td>
<td><%= #peptide.submitter.name rescue "" %></td>
<td <%= sorttable_customkey_from_date(#peptide.created_at)%> >
<%= #peptide.created_at.strftime("%b %d %Y") rescue "Unknown"%>
</td>
<td <%= sorttable_customkey_from_date(#peptide.updated_at)%> >
<%= #peptide.updated_at.strftime("%b %d %Y") rescue "Unknown"%>
</td>
<td><%= #peptide.sequence%></td>
<td><%= #peptide.modifications%></td>
<td><%= #peptide.vendor%></td>
<%= buttons() %>
</tr>
<%end%>
<%= will_paginate #peptides %>
</table>
<br>
<%= submit_tag "Create Spreadsheet"%>
The default list is grouped by status ordered.
however when I select any other status and submit the form the pagination links take me back to the default status.
Please help me resolve this issue.
Thanks
Without seeing the view, it sounds like you need to add the current params as an argument to the links for the other statuses...
Update
Try adding the params to your status link:
<%= link_to #peptide.name, peptide_path(#peptide, params), :action => :report, :id => #peptide.id %>
The documentation is here.

Rails duplicate loop - Hash and array loop

In my view I have:
<% #results.each_pair do |country_code, available| %>
<% #prices.each do |cc,domain| %>
<% klass = available.registered? ? "pinfo" : "info" %>
<span class="<%= klass %>"></span>
<%= #domain + country_code %> <%= domain.send(cc) %>$<br />
<% end %>
<% end %>
And the output is:
asdsaddk 8$
asdsaddk 1$
asdsadcom 8$
asdsadcom 1$
My controller:
def domain
country_codes = %w[ dk com ]
#domain = "asdsad"
#results = { }
#prices = { }
country_codes.each do |cc|
#results[cc] = Whois.whois("#{#domain}.#{cc}")
#prices[cc.to_sym] = Domain.order(cc).first
end
render :layout => false
end
How do I create a normal loop like where the output is not duplicate like:
asdsaddk 8$
asdsadcom 1$
Replace:
<% #results.each_pair do |country_code, available| %>
<% #prices.each do |cc,domain| %>
<%= #domain + country_code %> <%= domain.send(cc) %>$<br />
<% end %>
<% end %>
With:
<% #prices.each do |cc,domain| %>
<%= #domain + cc.to_s %> <%= domain.send(cc) %>$<br />
<% end %>
Indeed, you don't use the available variable from #results.
Sidenote: once again, you don't have any array here, only Hashes.
Reorganization needed:
def domain
country_codes = %w[ dk com ]
#domain = "asdsad"
#output = { }
country_codes.each do |cc|
#output[cc.to_sym] = { :whois => Whois.whois("#{#domain}.#{cc}"),
:domain => Domain.order(cc).first }
end
render :layout => false
end
In your view:
<% #output.each do |cc, hash| %>
<span class="<%= hash[:whois].registered? ? "pinfo" : "info" %>"></span>
<%= #domain + key.to_s %> <%= hash[:domain].send(cc) %>$<br />
<% end %>

Resources