ActiveRecord::RecordNotFound in ArticlesController#show - javascript

I want to implement ajax in my rails application but I am getting this error.
my erb code where ajax call is made is below
<% #articles.each do |article| %>
<tr>
<td><%= article.title %></td>
<td><%= article.text %></td>
<td><%= link_to 'Show', article_path(article) %></td>
<td><%= link_to 'Edit', edit_article_path(article) %></td>
<td><%= link_to 'Show Comment', :action => 'showcomment' ,method: :get, :id =>article, :remote => true ,:class=>'show_comment' %></td>
<td><%= link_to 'Destroy', article_path(article), method: :delete, data: { confirm: 'Are you sure?' } %></td>
</tr>
<% end %>
my articles.controller has code
class ArticlesController < ApplicationController
def new
#article = Article.new
end
def create
#article = Article.new(article_params)
if #article.save
redirect_to #article
else
render 'new'
end
end
def show
#article = Article.find(params[:id])
end
def edit
#article = Article.find(params[:id])
end
def index
#articles = Article.all
end
def destroy
#article = Article.find(params[:id])
#article.destroy
redirect_to articles_path
end
def showcomment
#article = Article.find(params[:article_id])
#comment = #article.comments.find(params[:id])
respond_to do |format|
format.js
end
end
def update
#article = Article.find(params[:id])
if #article.update(article_params)
redirect_to #article
else
render 'edit'
end
end
private
def article_params
params.require(:article).permit(:title, :text)
end
end
I dont know somehow the request is getting in show method and it is giving the exception
Couldn't find Article with 'id'=showcomment

In your view, try passing:
<td><%= link_to 'Show Comment', :action => 'showcomment' ,method: :get, :id =>article.id, :remote => true ,:class=>'show_comment' %>
Once the error is removed, try checking if your js template is in the right directory.
P.S: A little thing worth noticing: instead of showcomment use show_comment. Ruby way.

Related

I am trying to add comments withour refresh a page

When I try to add a comment, it doesnt append on table. When i refresh a page then it append. I dont know what is problem. I think I did everything well. There is no errors on page. And it goes in table whatever I add to table, but only after refresh a page.
show.html.erb
...
<table id="comments">
<tbody>
<% #article.comments.each do |comment| %>
<%= render 'comments/comment', comment: comment %>
<% end %>
</tbody>
...
_comment.html.erb
<tr>
<td><p><%= comment.name %></p></td>
<td><p><%= comment.body %></p></td>
<td><p><%= time_ago_in_words(comment.created_at) %> Ago</p></td>
<% if User.find_by(email: comment.name) == current_user %>
<td><%= link_to 'Delete', [comment.article, comment], method: :delete, data: { confirm: 'Are you sure?' } %></td>
<% else %>
<td> </td>
<% end %>
</tr>
create.js.erb
$('table#comments tbody').append("<%= j render #comment %>")
terminal
ActionController::UnknownFormat (ActionController::UnknownFormat):
app/controllers/comments_controller.rb:7:in `create'
routes.rb
Rails.application.routes.draw do
get 'search/index'
devise_for :users
get 'welcome/index'
get '/search', to: 'search#search'
resources :user
resources :articles do
resources :comments
member do
put "like" => "articles#like"
put "unlike" => "articles#unlike"
end
end
resources :search, only: [:index]
root 'welcome#index'
end
comments_controller.rb
def create
#article = Article.find(params[:article_id])
#comment = #article.comments.create(params[:comment].permit(:name, :body))
#comment.name = current_user.email
respond_to do |format|
if #comment.save
format.js
format.html { redirect_to #comment }
format.json { render :show, status: :created, location: #comment }
else
end
end
end
Because by default, format return from controller is html. So you need to add another formant js in controller to make js.erb work.
Your controller should be something like this:
def create
............
if #comment.save
respond_to do |format|
format.js
end
end
end
to handle the errors: in create.js.erb file, check #comment.errors.any? - then do whatever you want to do.

Ajax and Rails Completed 406 Not Acceptable

I'm completely lost as to how to make this request go through ajax without throwing back a 406 error. I am trying to add an item to a cart with ajax, and the item does get added and after a refresh the cart is updated. All I receive as an xhr notice with the 406 error. Any help is highly appreciated.
Product Controller
class ProductsController < ApplicationController
def index
#products = Shoppe::Product.root.ordered.includes(:product_categories, :variants)
#products = #products.group_by(&:product_category)
end
def show
#product = Shoppe::Product.root.find_by_permalink(params[:permalink])
end
def buy
#product = Shoppe::Product.root.find_by_permalink!(params[:permalink]) || params[:variant] ? Shoppe::Product.root.find_by_permalink!(params[:permalink]).variants.find(params[:variant].to_i) : #product
current_order.order_items.add_item(#product, 1)
respond_to do |format|
format.js
end
end
end
Show.html.erb
<h2><%= #product.name %></h2>
<% if #product.default_image %>
<%= image_tag #product.default_image.path, :width => '200px', :style => "float:right" %>
<% end %>
<p><%= #product.short_description %></p>
<p>
<% if #product.has_variants? %>
<% #product.variants.each do |v| %>
<%= form_tag product_path(#product.permalink, #product.permalink, :variant => v.id ),id: '#submit-form', remote: true do %>
<%= submit_tag 'Add to basket', :disabled => !v.in_stock? %>
<% end %>
<% end %>
<% else %>
<b><%= number_to_currency #product.price %></b>
<%= link_to "Add to basket", product_path(#product.permalink), :method => :post %>
<% end %>
</p>
<hr>
<%= simple_format #product.description %>
<hr>
<p><%= link_to "Back to list", root_path %></p>
routes.rb
Rails.application.routes.draw do
mount Shoppe::Engine => "/admin"
get "product/:permalink", to: "products#show", as: "product"
post "product/:permalink", to: "products#buy", as: "buy"
get "basket", to: "orders#show"
delete "basket", to: "orders#destroy"
root to: "products#index"
end
products.js.erb
$(document).ready(function() {
var data = $('#submit-form').attr('action')
$.ajax({
type: 'POST',
url: data
});
});
Looking up what format.js does, I found this: rails respond_to format.js API
It seems format.js in your buy action will render the buy.js file. You haven't shown this file, so I'm figuring it doesn't exist.
I'm figuring what you're trying to do is render json, which is simple enough. You could replace:
respond_to do |format|
format.js
end
with this:
render json: <your object>.to_json
make sure to strip any private data before sending the response.
By the way, you should probably be attaching a callback to your $.ajax call.

Toggle Button Action OnClick - JQuery + Rails

I would like to implement a Subscribe/Unsubscribe toggle button which creates/destroys a Subscription objectonClick, but I'm having difficulties finding an elegant solution.
I have experimented with multiple ideas, and have come to the conclusion that I need to use Javascript to accomplish this. However, I'm unsure if/how I can simultaneously change the button text and its action when a user clicks it. See button_to 'Subscribe' and button_to 'Unubscribe' below.
Any feedback or advice would be much appreciated!
Artists Index View:
<% #artists.each do |artist| %>
<tr id="tr_<%=artist.id%>">
<td><%= artist.name %></td>
<td><%= artist.artist_data["name"] %></td>
<td><%= artist.artist_data["facebook_tour_dates_url"] %></td>
<td><%= artist.artist_data["mbid"] %></td>
<td><%= artist.artist_data["upcoming_event_count"] %></td>
<% if artist.is_not_subscribed?(user_id: #user.id, artist_id: artist.id)%>
<td><%= button_to 'Subscribe', user_subscriptions_path(#user, artist_id: artist.id), method: :post, id: "subscribe_link_#{artist.id}", class: "subscribe", remote: true %></td>
<% else %>
<td><%= button_to 'Unsubscribe', user_subscription_path(#user, artist.find_subscription(user_id: #user.id, artist_id: artist.id)), method: :delete, id: "unsubscribe_link_#{artist.id}", class: "unsubscribe", remote: true %></td>
<% end %>
<% end %>
Subscriptions Controller:
def create
#user = User.find(params[:user_id])
#subscription = #user.subscriptions.build(subscription_params)
#subscription.artist_id = params[:artist_id]
respond_to do |format|
if #subscription.save
format.html { redirect_to artists_path, notice: 'Subscription was successfully created.' }
format.json { render :show, status: :created, location: #subscription }
format.js
else
format.html { render :new }
format.json { render json: #subscription.errors, status: :unprocessable_entity }
format.js { render js: #subscription, notice:'Unable to create Subscription' }
end
end
end
def destroy
#subscription = Subscription.find(params[:id])
#subscription.destroy
respond_to do |format|
format.html { redirect_to user_subscriptions_url, notice: 'Subscription was successfully destroyed.' }
format.json { head :no_content }
format.js
end
end
Subscription Model:
class Subscription < ActiveRecord::Base
belongs_to :artist
belongs_to :user
accepts_nested_attributes_for :artist
end
Artist Model:
class Artist < ActiveRecord::Base
include Subscribable
has_and_belongs_to_many :events
has_many :subscriptions
has_many :users, through: :subscriptions
validate :artist_already_exists?
end
User Model:
class User < ActiveRecord::Base
include Subscribable
has_many :subscriptions
has_many :artists, through: :subscriptions
accepts_nested_attributes_for :subscriptions
end
Drawing inspiration from this blog post, I was able to implement the following solution. If you have feedback or advice on how to better design this, don't be shy. I would appreciate your thoughts.
TLDR: Added a link_to_toggle method to clean up the view. Utilized Javascript's replaceWith to call link_to_toggle on each link click.
views/artists/index.html.erb
<% #artists.each do |artist| %>
<tr id="tr_<%=artist.id%>">
<td><%= artist.name %></td>
<td><%= artist.artist_data["name"] %></td>
<td><%= artist.artist_data["facebook_tour_dates_url"] %></td>
<td><%= artist.artist_data["mbid"] %></td>
<td><%= artist.artist_data["upcoming_event_count"] %></td>
<td><%= link_to_toggle_user_subscription(user:#user, artist:artist)%></td>
<td><%= link_to 'Edit', edit_artist_path(artist) %></td>
<td><%= link_to 'Destroy', artist, method: :delete, data: { confirm: 'Are you sure?' } %></td>
</tr>
<% end %>
helpers/subscriptions_helper.rb
module SubscriptionsHelper
def link_to_toggle_user_subscription(user:user, artist:artist)
if user.is_subscribed?(user_id: user.id, artist_id: artist.id)
link_to('Unsubscribe', user_subscription_path(#user, artist.find_subscription(user_id: #user.id, artist_id: artist.id), artist_id: artist.id),
method: :delete,
id: "unsubscribe_link_#{artist.id}",
class: "unsubscribe",
remote: true)
else
link_to('Subscribe', user_subscriptions_path(#user, artist_id: artist.id),
method: :post,
id: "subscribe_link_#{artist.id}",
class: "subscribe",
remote: true)
end
end
end
controllers/subscriptions_controller.rb
def create
#user = current_user
#artist = Artist.find(params[:artist_id])
#subscription = #user.subscriptions.build(subscription_params)
#subscription.artist_id = params[:artist_id]
respond_to do |format|
if #subscription.save
format.html { redirect_to artists_path, notice: 'Subscription was successfully created.' }
format.json { render :show, status: :created, location: #subscription }
format.js
else
format.html { render :new }
format.json { render json: #subscription.errors, status: :unprocessable_entity }
format.js { render js: #subscription, notice:'Unable to create Subscription' }
end
end
end
def destroy
#user = current_user
#subscription = Subscription.find(params[:id])
#artist = Artist.find(params[:artist_id])
#subscription.destroy
respond_to do |format|
format.html { redirect_to user_subscriptions_url, notice: 'Subscription was successfully destroyed.' }
format.json { head :no_content }
format.js
end
end
views/subscriptions/create.js.erb
$('#subscribe_link_<%=#artist.id%>').replaceWith("<%=j link_to_toggle_user_subscription(user:#user, artist:#artist)%>");
views/subscriptions/destroy.js.erb
$('#unsubscribe_link_<%=#artist.id%>').replaceWith("<%=j link_to_toggle_user_subscription(user:#user, artist:#artist)%>");

Submit Rails from on change of selected value in dropdown form

I have a Rails app with listing of leads in a table. In one of the collumns I display status of a lead in a drop down menu. I want to enable changing this status of the lead on changing the value selected in the drop down.
This is what I tried:
The code to display the form in a table cell:
<% #leads.each do |lead| %>
<tr>
<td><%= lead.id %></td>
<td><%= form_for(lead,:url => 'update_lead_status') do |f| %>
<div class="field">
<%= f.select :status, ["to_call","called","confirmed","lite"], :selected => lead.status, onchange: "this.form.submit();" %>
</div>
<% end %>
</td>
my update_lead_status method in leads controller:
#PUT
def update_lead_status
#lead = Lead.find(params[:id])
respond_to do |format|
# format.js
if #lead.update_attributes(params[:lead])
format.html { redirect_to leads_url, notice: 'Lead was successfully updated.' }
format.json { head :no_content }
else
format.html { render action: "edit" }
format.json { render json: #lead.errors, status: :unprocessable_entity }
end
end
end
Also I want the submission to be Ajax style without refreshing.
Set form id and then submit form
<%= form_for(lead,:url => 'update_lead_status',:html=>{:id=>'lead_form'}) do |f| %>
<%= f.select :status, ["to_call","called","confirmed","lite"], :selected => lead.status, onchange: "$('#lead_form').submit();" %>
<% end %>

Rails Dynamic variable at link_to with JS

I have form to showing all list from some filter form with js and also another button that direct to another action on the same controller BUT still carry the value of the form filter.
For the js things had done properly, but for the the other button, I still confuse.
My BalanceTransactions controller:
def end_period
#some coding
respond_to do |format|
format.html
format.js
end
end
def end_period_close
year=params[:year]
respond_to do |format|
format.html { redirect to goal_path }
end
end
My end_period.html.erb:
<%= form_tag end_period_balance_transactions_path, :method => "get", :id => "headers_search" do %>
<td><%= select_year(Date.today, :prompt => 'Choose year') %></td>
<td><%= submit_tag "Check", :name => nil, :class => "btn btn-info", :remote => true %></td>
<td><%= link_to "Close", nil, :id => "close_button", :class => "btn btn-danger" %></td>
<% end %>
<%= render :partial => 'end_period_table' %>
When I click on [Check] button rails re-render the partial, and it done nicely work with the filter. And I still confuse on how I can deliver the [year] dynamicaly for the [Close] button.
I also done trying with the balance_transactions.js.coffe, which:
$ ->
$("#close_button").click ->
year = $("#date_year").val()
$.get("end_period_close", { year: year })
Sorry for the bad question and grammar, first post.
Thanks and regard,
Kristono Sugiarto
try this one
$ ->
$('#close_button').click ->
$.ajax
url: 'your url here' # appending .erb to the filename gives you access to named routes
data:
year: $('#date_year').val()

Categories