Ruby on Rails Model creation string not converted to integer - ruby-on-rails

Here is my code:
base_release_id column in release db is integer type
form.html.haml
= form_for #release do |f|
= f.label :name
%br
= f.text_field :name
....
= f.label :base_release_id
%br
= f.select :base_release_id, options_from_collection_for_select(conditionsPlusBlankOrderBy(Release),"id","name",#release.base_release_id)
= f.submit
releases_controller.rb
def create
ap params
#release = Release.new(params[:release])
ap #release
...
end
I was going to create a new release including its name , base release id etc.
I was using 2 "ap" to trace the release object. strange thing happen. See my log below:
{
"utf8" => "â",
"authenticity_token" => "8HdDlC3jJxYvq+8tUh/cut5ibHxjIF6L2CzAFORlNBg=",
"release" => {
"name" => "e",
"code" => "e",
"base_release_id" => "2"
},
"commit" => "Create Release",
"action" => "create",
"controller" => "releases"
}
#<Release:0x000000190f06b8> {
:id => nil,
:name => "e",
:code => "e",
:base_release_id => nil,
}
Processing by ReleasesController#create as HTML
Parameters: {"utf8"=>"â", "authenticity_token"=>"8HdDlC3jJxYvq+8tUh/cut5ibHxjIF6L2CzAFORlNBg=", "release"=>{"name"=>"e", "code"=>"e", "base_release_id"=>"2"}, "commit"=>"Create Release"}
Not sure why base_release_id lost, name and code is working.
I have the similar code works in other page, in which case parame string value don't parsed to model integer?
it works if i added the datatype convertion as below:
def create
ap params
#release = Release.new(params[:release])
#release.base_release_id = params[:release][:base_release_id].to_i if params[:release][:base_release_id]
ap #release
...
end
Please help and thank you in advance.

found why.
in my model release.rb, i'v defined "attr_accessible :id, :name, :code, :as => :tmp_use". Then it accept id, name and code only. After i added :base_release_id, it works.
not sure how :as => :tmp_use work. I suppose default all variable can be accessed. In some places, i was using
Release.new("id"=>row[:id],"name"=>row[:name],"code"=>row[:code], :as => :tmp_use)
Some places i don't want to do it i want to all columns be accessable.
No sure how.
Thank you Ivan anyway.

Related

Access params with wildcard in Rails

At the moment I have a form_tag which contains inputs and puts these inputs into parameters.
I want to be able to loop over them in the controller action.
I've tried getting all params excluding all the usual params (action, controller, model name etc.) and then using a wildcard like params[:prop*].
Here is the offending form inputs:
%input{:name => "userEmails", :id =>"userEmails", :type => "hidden", :value => ""}
-#all_properties.each do |prop|
%input{:name => "prop"+prop.name+"checkbox", :type => "checkbox", :id => "prop"+prop.name+"checkbox"}
#{prop.name}
%input{:name => "prop"+prop.name, :type => "text", :id => "prop"+prop.name}
These show up in params like {"propProperty1checkbox"=>"on", "propProperty1" => "testing", "propAnotherPropertycheckbox" => "on", "propAnotherProperty" => "another test value"} etc.
I'm unsure how to access these as the names of the properties can change and so need to be accessed abstractly.
You can use #select on params hash to filter only the params that are interesting for you:
params = {"user_id"=>1,
"propProperty1checkbox"=>"on",
"propProperty1"=>"testing",
"propAnotherPropertycheckbox"=>"on",
"propAnotherProperty"=>"another test value"
}
params.to_h.select{|key, value| key =~ /^prop/}
#=> {"propProperty1checkbox"=>"on",
#"propProperty1"=>"testing",
#"propAnotherPropertycheckbox"=>"on",
#"propAnotherProperty"=>"another test value"}
EDIT
Example from the comment:
[13] pry(main)> {"utf8"=>"✓", "_method"=>"put", "authenticity_token"=>"xxxxx", "userEmails"=>"teste#test.com,test2#test.com,test4#test.com,fasd#gmail.com", "propProperty1checkbox"=>"on", "propProperty1"=>"3", "propAnotherPropertycheckbox"=>"on", "propAnotherProperty"=>"4", "commit"=>"Submit", "Application"=>"8", "Company"=>"1" }.to_h.select{|k, v| k =~ /^prop/}
=> {"propProperty1checkbox"=>"on",
"propProperty1"=>"3",
"propAnotherPropertycheckbox"=>"on",
"propAnotherProperty"=>"4"}
You can try something like:
input(name: "props[#{pro_name}][checkbox]"...)
input(name: "props[#{pro_name}][text]"...)
Then, in your controller:
def method
props = params[:props]
props.each do |property_name, values|
chk = values[:checkbox]
text = values[:text]
end
end

How to update values that depend on strong params

I have an action (using strong parameters) in controller:
def home_task_params
params.require(:home_task).permit(:subject, :description, :data)
end
I want to modify the data before recording to the database. I want to do something similar to this:
def create
#home_task = HomeTask.create(
:subject => home_task_params.subject,
:description => home_task_params.description,
:day => home_task_params.data,
:data => home_task_params.data,
:class_room => current_user.class_room
)
end
How do I implement it?
params is an object that behaves like a hash. Therefore you cannot read values from that object like this params.subject instead, you have to use params[:subject].
Something like this might work:
#home_task = HomeTask.create(
:subject => home_task_params[:subject],
:description => home_task_params[:description],
:day => home_task_params[:data],
:data => home_task_params[:data],
:class_room => current_user.class_room
)
Or you could just merge the additional values to params:
#home_task = HomeTask.create(
home_task_params.merge(
day: home_task_params[:data],
class_room: current_user.class_room
)
)

update_all ruby on rails

Im trying to update all post where a condition is true. If the condition is true should the field category_id be set to params[:category_id]
Every time im trying to do it will my code update all post where the condition is true and set it to "--- !ruby/hash:ActionController::Parameters categori_id: '169'"
Instead of just 169.
My controller action look like this
def update_all_notes
#deletefolder = Categori.find(params[:id])
System.where(:categori_id => params[:id]).update_all(:categori_id => params[:categori_id])
redirect_to :back
end
My form look like this:
<%= form_tag update_all_notes_path(category.id) do %>
<%= collection_select :kategori_id, :id, #current_company.category.where.not(:name => category.name), :id, :name %>
<button>move</button>
this is the parameters i send to the action
"categori_id"=>{"categori_id"=>"169"},
"id"=>"168"}
Thanks in advance
From your hash you should replace params[:categori_id] to be params[:categori_id][:categori_id]
as the hash is { "categori_id" => {"categori_id" => 169}, "id" => X }
Example of update_all use:
ids = [1,2,3]
records = Mammal::Human.where(id: ids)
records.update_all(status: :enlightenment, enlightenment_at: Time.zone.now, enlightenment_by: "myself")
I will rather use status: value over :status => value syntax

Rails Multiple Select boxes: Injecting default values from params

I currently have a multiple select box in a rails form that looks like this:
= select_tag :in_all_tags, options_from_collection_for_select(Tag.where(:project_id => #project.id), :id, :name, #in_all_tags_param), { :id => "tags", :tabindex => "3", "data-placeholder" => "Choose Tags", :multiple => "multiple" }
Where
#in_all_tags_param = params[:in_all_tags]
The problem is, #in_all_tags_param will only populate the select form with the last value from params[:in_all_tags]. So, if the url string reads in_all_tags=5&in_all_tags=8, the pre-selected value in the multiple select will only be 8.
From what I understand, the way around this is to append [] to the field name for multiple params, so that :in_all_tags becomes in_all_tags[]
BUT, when I try this, submitting the form returns:
Expected type :default in params[:in_all_tags], got Array
Any suggestions appreciated.
Cheers...
You need to add a :name element to the same hash with :multiple => true in it. So I use something similar for Genres on an app for mine and I do { :multiple => true, :name => "lesson[genre_ids][]" }. The name has to be model[attribute][].

Passing different parameter to a method call depending on a condition in Ruby

This is the code for my function, in which I am making a call to new
def create_person_detail_from_registration(type, registration, registration_detail)
person_detail = type.constantize.new(
:email => registration.email_2,
:phone_1 => registration_detail.phone_1,
:phone_2 => registration_detail.phone_2,
:phone_3 => registration_detail.phone_3,
:phone_4 => registration_detail.phone_4,
:phone_5 => registration_detail.phone_5,
:phone_6 => registration_detail.phone_6,
:phone_7 => registration_detail.phone_7,
:address_1 => registration_detail.address_1,
:address_2 => registration_detail.address_2,
:city => registration_detail.city,
:state => registration_detail.state,
:postal_code => registration_detail.postal_code,
:country => registration_detail.country
)
return person_detail
end
Now the issue is depending on what value type has, :email is either set to registration.email_2 or registration.email. One way of doing that is of course, to write the whole code twice surrounded by an if-elsif statement. But I just wanna know, if there's any smarter, more elegant way of doing this?
Just add the condition into value .
:email => (type==1 ? registration.email_2 : registration.email),

Resources