following were my javascript where user post the updates:
$('.attachments-container').on('click', '.cover-attachment', function(event) {
var attachment_id = $(this).parent().find('input[name="product_attachment[id][]"]').val();
$.ajax({
type: "POST",
url: "/products/update_cover",
dataType: "json",
data: attachment_id,
complete: function(){
console.log('change completed');
}
});
event.preventDefault();
})
On my routes:
resources :products do
member do
match "update_cover", via: [:post]
post "update_cover" => 'products#update_cover'
end
end
On my controller:
class ProductsController < ApplicationController
skip_before_action :authenticate_user!, only: [:result, :show]
def update_cover
#attachment_id = params[:attachment_id]
render :json => {:status => 'success'}.to_json
end
end
I had no clue where this error comes from: ActionController::RoutingError (No route matches [POST] "/products/update_cover"): Thanks!!
If you run rake routes in your terminal you will see that you do not have a route for products/update_cover. You have - products/:id/update_cover. Since you have defined it as a member route, you need to pass the parent_id as part of the route. Try this
url: "/products/" + attachment_id + "update_cover",
And you dont need to pass attachment_id in the data hash.
Incidentally, the 2 routes you posted essentially do the same thing. You can lose
match "update_cover", via: [:post]
Related
I have an ajax post to my backend rails app, it's to post a upload a file.
Post response with my files list in JSON
After that I need to reload my files list at view detalhes.html.erb page. This list is a partial. Here is what I have:
controller method:
def upload_arquivo
#ponto_venda = PontoVenda.find(params[:pv_id])
nome = params[:key].split('/').last
#arquivo = Arquivo.new(nome: nome, endereco: params[:url], s3_key: params[:key], tamanho: params[:tam], user_id: params[:u_id], tag_id: params[:tag])
if #arquivo.save!
ArquivoPontoVenda.create(arquivo_id: #arquivo.id, ponto_venda_id: #ponto_venda.id, fachada: false)
response = { files: filtro_pv_arquivos, message: "O arquivo '#{nome}' foi salvo" }
else
response = { files: '', message: 'Ocorreu um erro ao salvar o arquivo, por favor, tente novamente' }
end
render json: response
end
My ajax post method at _arquivos_upload.html.erb:
$.ajax({
url: 'some_url,
type: 'post', processData: false
})
.success(function(data) {
console.log(data.files.length);
// trying to reload partial after post request
$('#display-arquivos').html("<%= escape_javascript(render "arquivos_buscados") %>");
});
data.files are correct, I just need to find a way to pass this to my render partial. How can I do that? Or if this is a bad way to do it, how can I do better?
Here is where I render my partial detalhes.html.erb:
<div class="card" id="display-arquivos">
<%= render "arquivos_buscados" %>
</div>
I already have try a lot of this:
github link
set .html(data.files)
use js.erb file logic
That looks good. I'd suggest modifying your partial to accept a local variable and then explicitly passing it in when you render the partial.
<div class="card" id="display-arquivos">
<%= render "arquivos_buscados", locals { files: #files #add this } %>
</div>
$('#display-arquivos').html("<%= escape_javascript(render "arquivos_buscados", locals: { files : data.files } ) %>");
I think I would render back html instead of json. Then, in .success function of the ajax call, just do:
$.ajax({
url: 'some_url,
type: 'post', processData: false
})
.success(function(data) {
$('#display-arquivos').html(data);
});
You'll probably need to change your controller action along the lines of:
def upload_arquivo
...
if #arquivo.save!
ArquivoPontoVenda.create(arquivo_id: #arquivo.id, ponto_venda_id: #ponto_venda.id, fachada: false)
#files = #populate your #files variable
render "arquivos_buscados"
else
render :something_else
end
end
I'm trying to wire up this AJAX POST request in my react component to communicate with my rails api controller. The console logs a 404 error and I can't seem to hit the pry.
react/src/pages/HomeIndex.js
getCompare() {
$.ajax({
url: '/api/sources/compare',
type: 'POST',
data: {value: this.state.inputValue, from: this.state.compareFrom, to: this.state.compareTo },
contentType: 'application/json'
})
}
controllers/api/sources_controller.rb
def compare
binding.pry
end
config/routes
post '/api/sources/compare', to: 'api/sources#compare'
namespace :api do
resources :sources, only: [:index, :compare]
end
rake routes
api_sources_compare POST /api/sources/compare(.:format) api/sources#compare
update
I tried updating the routes with several permutations...
namespace :api do
resources :sources, only: [:index] do
collection do
post :compare
end
end
end
namespace :api do
resources :sources, only: [:index, :compare] do
collection do
post :compare
end
end
end
namespace :api do
resources :sources, only: [:index] do
collection do
resources :compare, only: [:compare]
end
end
end
namespace :api do
resources :sources do
post :compare
end
end
...all with the same outcome.
You can solve this by stringifying your AJAX payload, as follows:
getCompare() {
let data = JSON.stringify({value: this.state.inputValue, from: this.state.compareFrom, to: this.state.compareTo })
$.ajax({
url: '/api/sources/compare',
type: 'POST',
data: data,
contentType: 'application/json'
})
}
I'm trying to pass a parameter through a url in an Ajax request that's triggered by a confirmation dialogue. I'd like to fetch the value of that parameter in my Rails controller given a successful request but I haven't been able to do it.
I've tried so far the following code:
Here my Ajax request where I've been adding the param in the URL plus other params in data
function continueSave() {
var name = $('#leader_name').val();
var persisted_time = $('#leader_time').val();
$.ajax({
type: "POST",
url: "/leaderboards/1/?test=1",
data: { leader: { name: name, time: time } },
success: success
});
}
Here the dialogue-related JS
function nameAlert() {
return confirm("Name already exists. Would you like to continue?");
};
(function() {
if (nameAlert()) {
continueSave();
}
else {
//something else here
}
})();
Although the request successfully reaches the controller there's params[:test] is nil in the controller.
I've also tried to pass the test param in data, but it is not working either.
Would appreciate some help.
The relevant controller action (leaders_controller.rb)
def create
#leader = Leader.new(leader_params)
#leader.leaderboard_id = #leaderboard.id
#name_repeated = !#leaderboard.leaders.find_by(name: #leader.name).nil?
#check = params[:test]
if params[:test].nil? && #name_repeated == true
render :template => 'leaders/repeated_name.js.erb'
else
#leader.save
#rank = #leader.rank_in(#leaderboard)
respond_to do |format|
if #leader.save
format.html { redirect_to root_path }
format.js { }
else
end
end
end
end
Note:
1.- 'leaders/repeated_name.js.erb' contains the code for the Ajax request
2.- In routes Leader resource is nested within Leaderboard resource
Sorry guys I found the mistake. It was a dumb one.
I have shallow nested routes so that leaders is nested in leaderboards, therefore I was using the incorrect path for the request. It should be:
$.ajax({
type: "POST",
url: "/leaderboards/1/leaders?test=1",
data: { leader: { name: name, time: time } },
success: success
});
I should have caught that before sorry for wasting your time.
I'll post here - my comments are getting too long.
Try adding { type: 1} to your data and changing type to GET. Rails params contain both GET and POST data - you don't even have to change your controller.
function continueSave() {
var name = $('#leader_name').val();
var persisted_time = $('#leader_time').val();
$.ajax({
type: "GET",
url: "/leaderboards/1/",
data: { leader: { name: name, time: time }, test: 1 },
success: success
});
}
I'm building an app, using Rails and Backbone as my back-end, that requires users to login to access certain pages. On one of the user authenticated pages, I have it setup so they can create an entry in my database, by entering in data, which is then sent to the Google Maps API to retrieve the latitude and longitude.
Via a helper function, I'm checking if the user is authenticated or not, but when I send up the AJAX call to Google Maps API, the user token is also being sent up. Here's the code that I have set up right now.
In my api js file, which is ran first on load for my page
var token = $('#api-token').val();
$.ajaxSetup({
headers:{
"accept": "application/json",
"token": token
}
});
In my users_controller.rb
def profile
authorize!
#user = current_user
#bathrooms = Bathroom.all.sort_by { |name| name }
render layout: 'profile_layout'
end
def authorize!
redirect_to '/login' unless current_user
end
def current_user
#current_user ||= User.find(session[:user_id]) if session[:user_id]
end
Here's my AJAX call
function getInfo(location) {
console.log('getInfo');
$.ajax({
method: 'get',
url: 'https://maps.googleapis.com/maps/api/geocode/json',
data:{address: location, key: 'API KEY GOES HERE'},
success: function(data) {
extractData(data);
}
})
}
You can try following steps:
function getInfo(location) {
console.log('getInfo');
delete $.ajaxSettings.headers["token"]; // Remove header before call
$.ajax({
method: 'get',
url: 'https://maps.googleapis.com/maps/api/geocode/json',
data:{address: location, key: 'API KEY GOES HERE'},
success: function(data) {
extractData(data);
}
});
$.ajaxSettings.headers["token"] = token; // Add it back immediately
}
If I render json in Ruby, how do I access the values in javascript?
In ruby, if I write:
response = {:key => "val"}
response = response.to_json
render :json => response, :status => 200
How would I access "val" in javascript?
If I do alert(response) in javascript, I see a tag surrounding the json, does this make a difference or is this expected?
I tried jQuery.parseJSON(response) but I got a syntax error. If I try to access response directly, I don't get the correct value- should
response.key === "val"
evaluate to true?
Am I setting it up incorrectly in Ruby or accessing it incorrectly in javascript, or both?
It would really help if you could show your javascript code.
Anyway, one way you can do it is to use jQuery's ajax function and set the dataType to json.
$.ajax({
type: "GET",
url: "<your link>",
dataType: "json",
success: function(response) {
if (response.key)
alert(response.key);
});
});
Hope this helps.
Here's a quick example.
In ./config/routes.rb
match '/index' => 'application#index'
match '/json' => 'application#json'
The controller, ./app/controllers/application_controller.rb:
class ApplicationController < ActionController::Base
protect_from_forgery
def index
# server side code required by index
end
def json
response = {:key => "val"}
response = response.to_json
render :json => response, :status => 200
end
end
The erb page an ajax request is made from, in this case ./app/views/application/index.html.erb:
<script type="text/javascript" charset="utf-8">
$(document).ready(
function(){
$("a#my_ajax").bind("ajax:success",
function(evt, data, status, xhr){
console.log(data.key);
console.log(data.key === "val");
}).bind("ajax:error", function(evt, data, status, xhr){
console.log("doh!")
});
});
</script>
<%= link_to "test", {:controller=>"application", :action => 'json'}, :remote=> true, :id => "my_ajax" %>