I'm trying to write an application that will have to interact with POST but I'm having issues accessing the parameters. This is not meant to be useful right now but I'm just trying to flash the result of the form. According to google dev tools, the POST parameter is set to 1.
Here's my routes.rb file
devise_scope :user do
put 'users/toggle_activation' => 'users/sessions#toggle_activation'
get 'users/sign_out' => 'users/sessions#destroy'
post 'pages/home' => 'users/sessions#activities'
end
This is the controller in question
def activities
params.permit(:tennis)
current_user.save
flash[:notice] = params[:tennis]
redirect_to root_path
end
This is the form code
<%= form_for :user do |f| %>
<%= f.check_box :tennis %>
<%= f.submit %>
<% end %>
Any help is appreciated.
If you're using "form_for", then the check_box name will result as "user[tennis]", not just "tennis". View source in your browser and you should see this.
Do something like the following in your controller method (although I'm not sure how it will be called with "form_for :user" because your "activities" route isn't in your routes.rb in the code above):
user_params = params.require(:user).permit(:tennis)
flash[:notice] = user_params[:tennis]
Related
I am completely new to RoR and was trying to build a simple blog, but already got stuck at the "Adding Post" function.
The following Error Message pops up when I load .../posts/new:
No route matches {:action=>"show", :controller=>"posts"} missing required keys: [:id]
Here is what my posts controller looks like this:
class PostsController < ApplicationController
def index
end
def new
end
def create
render plain: params[:post].inspect
end
end
Here is what my new.html.erb looks like this:
<h1>Add Post</h1>
<%= form_for :post, url: posts_path do |f| %>
<p>
<%= f.label :title %><br>
<%= f.text_field :title %>
</p>
<p>
<%= f.label :body %><br>
<%= f.text_area :body %>
</p>
<p>
<%= f.submit %>
</p>
<% end %>
I had set posts as resource in my routes. The surprising thing is, that on my friend's laptop, the code works.
I would be very happy about any advice, and apologize for the silly question.
The form_for helper is looking for a resource object to operate with, and you're giving it a symbol. I suspect it's assuming that's an action URL instead, and translating (or trying to) that symbol into a route.
Using form_for in a new action, the pattern is usually to create a new resource and feed that into the form_for helper:
def new
#post = Post.new
end
<%= form_for #post, url: posts_path do |f| %>
...
<% end %>
Check your routes with:
$rake routes
And you'll see that the posts_path with an id its used to update a "post" and not to create one, you'll also found the path you want to create a new "post".
You might say: but i don't have an update action. If on your routes file you used the resources keyword you do, even if the action itself is missing.
Update:
Remove the
url: post_path
From your form_for call
My recommendation, check out the rails guides on routing.
I was following the instructions on the wiki for this gem:
https://github.com/mislav/will_paginate/wiki
And it works great for my listings controller :/ I was able to get them paginate but I have no idea how to get it work with my comments. My comments controller doesn't have a show method.
class CommentsController < ApplicationController
before_action :authenticate_user!, :except => [:show]
def create
#comment = Comment.new(params[comment_params])
#comment.listing_id = params[:listing_id]
#comment.user_id = current_user.id
#comment.body = params[:comment][:body]
if #comment.save
flash[:success] = "Comment Successful."
redirect_to listing_path(#comment.listing)
else
flash[:alert] = "Comment Failed."
end
end
def destroy
#comment = #listing.comments.find(params[:id])
#comment.destroy
flash[:success] = "Comment Removed."
redirect_to listing_path(#listing)
end
private
def comment_params
params.require(:comment).permit(:user, :body)
end
end
This is the show method I have inside my ListingsController:
def show
#comment = Comment.new
#comment.listing_id = #listing_id
end
It's what sets the comments to my understanding
This is the listings/show.html.erb file's part where it renders the comments:
<div class="commentblock">
<div class="text-left">
<%= render partial: 'comments/form' %>
<%= render partial: 'listings/comment', collection: #listing.comments.reverse %>
</div>
</div>
I know the first part of ruby code actually renders the forms but I don't understand how or what the collection part works or how to apply the pagination to this.
The listings/comment file looks like this:
<div class="panel panel-default">
<div class="panel-heading"><%= comment.user.username %>: <%= time_ago_in_words(comment.created_at)%> ago</div>
<div class="panel-body">
<%= comment.body %>
</div>
</div>
I've tried quite a few things but I still don't really get where or what to change in my code. I went into the listing/comment and tried adding:
<%= will_paginate(comment) %> # this crashed, undefined method `total_pages' for #<Comment:0x007ff556a36468>
EDIT: The will_paginate wiki says you to pass a paginated array when you get the error I got, but I don't know that is done >.>; it doesn't show how you would do that...
EDIT:
http://csnipp.com/s/709 this website said all you had to do was create a file config/initializers/will_paginate.rb and place this line of code in it:
require 'will_paginate/array'
But that didn't help
EDIT:
If you guys need to see more of the code it's actually on github:
https://github.com/ilovemysillybanana/pastie/
I'm really stuck on this D: I followed a tutorial on how to make the comments but theirs didn't paginate.
EDIT:
I fixed it!
The way to do it was by replacing this line:
<%= render partial: 'listings/comment', collection: #listing.comments.reverse %>
with this line:
<%= render partial: 'listings/comment', collection: #list_comments = #listing.comments.paginate(:page => 1, :per_page => 5) %>
But for some reason I don't get the numbers to change the comment pages :/
<%= render partial: 'listings/comment', collection: #listings = #listing.comments.reverse.paginate(:page => params[:page], :per_page => 10) %>
My code was correct, what I wasn't realizing is that #listings or #list_comments was creating a local variable that needed to be paginated itself. I was trying to find a way to paginate either in one command(which if possible I don't care, but if you know how it'd be nice to know for the future I guess) anyway, all that I needed to do to fix this was add this:
<%= will_paginate #listing_comments %>
I want to use a button inside HTML using information from the HTML itself.
More in detail:
There is a html.erb file. In there lay 2 <input type="hidden" name="Name" value='Tom'> and a Button.
Within the html.erb file i could get the value by typing params['Name']. But here comes my Problem. I have no idea how to write a button, so that it will only save #user when i click it. Therefore the method of the button should be something like:
#user.name = params["Name"]
#user.age = params["Age"]
#user.save
For me it looks like the simplest if i had this method(of the button) within the html, where #user, the name and the age are stored. But i'm a new to ruby, so what do i know.
In your controller where you have access to the params['Name'] and params['Age'] to save or update an existing one:
#user.name = params["Name"]
#user.age = params["Age"]
#user.save
A more Rails-y way, however is to use form_for to create a form for an object:
# show.html.erb (or whatever controller action the view is for)
<% form_for #user do |f| %>
<%= f.text_field :name %>
<%= f.text_field :age %>
<%= button_to "Save User" %>
<% end %>
# user_controller.rb
# If creating:
#user = User.new(params[:user])
# or for updating: (no need for save)
# #user.update_attributes(params[:user])
#user.save
Since the :age and :name will be passed in the :user hash looking like this:
user: {
name: "John",
age: 18
}
which can be passed to User.new or #user.update_attributes and it will set #user.name and #user.age from the hash.
I suggest browsing the saving data in the controller section of the Rails guides
I'm working on a form that should allow users to update a session variable called session[:city] that tracks their location. The variable doesn't need to be saved in the database cause it's kind of a throwaway; it only needs to exist while the user is on the site.
session[:city] is used in several places throughout the site, so I've placed the following method in the Application Controller:
class ApplicationController < ActionController::Base
before_filter :set_city
def set_city
unless session[:city].present?
session[:city] = request.location.city
end
if params[:city].present?
session[:city] = params[:city]
end
end
end
That part works correctly, and I'm able to call the variable throughout the site.
The issue I'm having is in updating the variable by a form. The only action I need it to do is update the variable, but it's not responding. I know I'm missing something here, but after trying a bunch of things I'm a bit stumped. This is my basic form currently:
<%= form_tag do %>
<%= text_field_tag :city, params[:city] %>
<%= submit_tag %>
<% end %>
Edited to working code
This will not work in production like environment where you have multiple worker process to serve the requests(unicorn or passenger). Each process will have its own memory. If the value is changed during a request processed by one worker process, other processes will not have the updated value.
You should be using session to store this information.
You can try something like this:-
<%= form_tag do %>
<%= text_field_tag :person, :city, :name => "city" %>
<%= submit_tag %>
<% end %>
class ApplicationController < ActionController::Base
before_filter :set_city
def set_city
unless session[:city].present?
session[:city] = params[:city] || request.location.city
end
end
end
The conditions needed to be split into 2 statements: an unless to set the session[:city] and an if to check if any params were being passed.
class ApplicationController < ActionController::Base
before_filter :set_city
def set_city
unless session[:city].present?
session[:city] = request.location.city
end
if params[:city].present?
session[:city] = params[:city]
end
end
end
And the working form:
<%= form_tag root_path do %>
<%= text_field_tag :city, params[:city], :placeholder => "#{session[:city]}: Change City" %>
<% end %>
I've been staring at this for a while and Google hasn't helped much so I'm turning to you guys for help. This should be a pretty simple fix.
The goal of the code is to take an email address from a sign up field and place it in the database.
I think most of what I need is there but I'm getting this error:
undefined method model_name for NilClass:Class
My home.html.erb file contains the following:
<%= form_for(#signup) do |f| %>
<div class="field">
<%= f.label :email %><br />
<%= f.text_field :email %>
</div>
<div class="actions">
<%= f.submit "Enter" %>
</div>
<% end %>
The model contains this:
class Signup < ActiveRecord::Base
attr_accessible :email
email_regex = /\A[\w+\-.]+#[a-z\d\-.]+\.[a-z]+\z/i
validates(:email, :presence => true,
:length => {:maxiumum => 40},
:format => {:with => email_regex})
end
The controller contains:
class SignupController < ApplicationController
def show
end
def new
#signup = Signup.new
end
def create
#signup = Signup.new(params[:id])
if #signup.save
else
render 'new'
end
end
end
The problem is most likely because of an instance variable that you're using in your form_for not being set to an ActiveRecord object. It appears that you are setting it correctly in your "new" action, but it's not clear that you're rendering the correct template since you mention the form being in "home.html.erb"?
Either way, ensure that whatever you're using in the form_for is set to a valid ActiveRecord object and your problem may be solved.
In addition, you may want to change your create action to use all the params from the form:
#signup = Signup.new(params[:signup])
Add this to the home action in the pages controller:
#signup = Signup.new
The reason for the error is that you are using #signup in your form, but you didn't define it in your show controller action.