param is missing or the value is empty for: quotes - ruby-on-rails

I have a POST request from a javascript file below:
this.submitQuoteButton = $("<button />")
.text("Download PDF")
.addClass("submitQuoteButton button-success pure-button")
.click(function() {
$.ajax({
type: "POST",
url: "../quotes/create",
data: {
name : "John ",
email: "john#john.com",
json: "data",
uid: "uid",
},
dataType:'text',
success: function(data,status,xhr){
console.log(status);
alert("SUCCESS!");
},
error: function(xhr,status,error){
console.log(status,error);
alert("ERROR!");
}
});
})
This POST calls to my quotes_controller create method where I have this
def create
#quote = Quote.new(quote_params)
if #quote.save
redirect_to root_url
else
redirect_to blog_path
end
end
private
def quote_params
params.require(:quotes).permit(:uid, :name, :email, :json)
end
The aim is to get the data passed in the POST request and save it to my database with the create method. Am I doing this right? I am getting a:
param is missing or the value is empty for: quotes
Does this mean there is a problem with my database set up or the create method?

quote_params require the quotes key in your params. So your ajax call data should look like this:
data: {
quotes: {
name : "John ",
email: "john#john.com",
json: "data",
uid: "uid",
}
}

Related

Rails 5.1.: cannot get JSON object from string

I'm a bit stuck with JSON parsing as I'm new to coding and this is my first time dealing with JSON :) I kind of figured out how to save JSON, but can't read it back from DB.
I have this Controller:
class Common::DatatablesStatesController < ApplicationController
require 'json'
def update
datatables_state.update(datatable_states_params)
render json: datatables_state
end
def show
table_state = current_user.datatables_states.where(name: params[:id]).select(:state)
state = JSON.parse(table_state)
render json: { state: state["state"] }
end
private
def datatable_states_params
params['common_datatable_state']['state'] = params['common_datatable_state']['state'].to_json
params.require(:common_datatable_state).permit(:user_id, :name, :state)
end
def datatables_state
#datatables_state ||= current_user.datatables_states.where(name: params[:id]).first_or_create
end
end
In terminal I see my Update action is working, however I cannot make Show action to work as it throws out this error:
TypeError (no implicit conversion of Common::DatatableState::ActiveRecord_AssociationRelation into String):
app/controllers/common/datatables_states_controller.rb:12:in `show'
app/controllers/application_controller.rb:41:in `set_current_user'
In my Pry I can do this:
[3] pry(main)> user.datatables_states.where(name: 'campaigns_index').select(:state)
Common::DatatableState Load (0.5ms) SELECT "common_datatable_states"."state" FROM "common_datatable_states" WHERE "common_datatable_states"."user_id" = $1 AND "common_datatable_states"."name" = $2 [["user_id", 2], ["name", "campaigns_index"]]
=> [#<Common::DatatableState:0x000000028e3f30
id: nil,
state:
"{\"time\":\"1494910215056\",\"start\":\"0\",\"length\":\"10\",\"order\":{\"0\":[\"0\",\"asc\"]},\"search\":{\"search\":\"\",\"smart\":\"true\",\"regex\":\"false\",\"caseInsensitive\":\"true\"},\"columns\":{\"0\":{\"visible\":\"true\",\"search\":{\"search\":\"\",\"smart\":\"true\",\"regex\":\"false\",\"caseInsensitive\":\"true\"}},\"1\":{\"visible\":\"true\",\"search\":{\"search\":\"\",\"smart\":\"true\",\"regex\":\"false\",\"caseInsensitive\":\"true\"}},\"2\":{\"visible\":\"true\",\"search\":{\"search\":\"\",\"smart\":\"true\",\"regex\":\"false\",\"caseInsensitive\":\"true\"}}}}">]
How do I get single JSON object from string I have in state field (JSON column, Postgres) from my DB, please? Thank you!
Update
This piece of code from application_controller.rb helped to access current_user outside Controllers:
#38 around_action :set_current_user
#39 def set_current_user
#40 Current.user = current_user
#41 yield
ensure
Current.user = nil
end
Update 2
After I updated show to this:
def show
table_state = current_user.datatables_states.where(name: params[:id]).select(:state).first
state = JSON.parse(table_state.state)
render json: { state: state }
end
I still don't see it loading my state drom DB with stateLoadCallback from JS below:
jQuery(document).ready(function() {
var user_id = $("#data-table").attr('data-user-id');
var contname = $("#data-table").attr('data-controller-name');
$('#data-table').DataTable(
{
"processing": true,
"serverSide": true,
"ajax": $('#data-table').data('source'),
stateSave: true,
"stateSaveCallback": function (settings, data) {
// Send an Ajax request to the server with the state object
$.ajax( {
"url": "/common/datatables_states/"+contname+".json",
"data": {"common_datatable_state":{"user_id": user_id, "name": contname, "state": data}} ,
"dataType": "json",
"type": "PATCH",
"success": function () {}
} );
},
stateLoadCallback: function (settings, callback) {
$.ajax( {
url: '/common/datatables_states/'+contname+'.json',
async: false,
dataType: 'json',
type: 'GET',
success: function (json) {
callback( json );
}
} );
}
}
);
});
The problem is that table_state is an ActiveRecord::Relation of Common::DatatableState as you point in your example. You are trying to parse the relation which is not a string.
What about this:
table_state = current_user.datatables_states.where(name: params[:id]).select(:state).first
state = JSON.parse(table_state.state)
render json: { state: state }

Rails select2 after create new tag i haven't id on create action

I use select2 and want to create new tags and then save them.
i have form for #cost and for select2 this
<%= f.collection_select :product_ids, Product.all,:id, :name ,{include_hidden: false},{ multiple: true} %>
for creation new product i have this js code
$(document).ready(function () {
$('#cost_product_ids').select2({
tags: true,
tokenSeparators: [",", " "],
createProduct: function (product) {
return {
id: product.term,
text: product.term,
isNew: true
};
}
}).on("change", function (e) {
var isNew = $(this).find('[data-select2-tag="true"]');
if (isNew.length) {
$.ajax({
type: "POST",
url: "/product_new",
data: {product: isNew.val()}
});
}
});
});
and controller method for save new product
def product_new
product = Product.find_by(name:params[:product])
Product.create(name:params[:product]) if !product
render json: :ok
end
cost create action
def create
#cost = Cost.new(costs_params)
if #cost.save
flash[:notice] = t('added')
if params[:add_more].present?
redirect_back(fallback_location: root_path)
else
redirect_to #cost
end
else
render action: 'edit'
end
end
def costs_params
params.require(:cost).permit(:day, :amount, :description, :source,:tag_list,:product_ids=>[])
end
it works ok, but when i want to save my #cost record with this newly created product i have received only name of my tag without id.
For example i have products water=>id:1,beer=>id:2,and create new juice tag in db it has id:3
on create in have params "product_ids"=>["1", "2", "juice"]
How to fix it?
you shouldn't use id: product.term,
but id: product.id,

How TO Get the email when we seleted the person name

I need an employee email-id when I'm selecting his name, if his email id is exist in database. Can any one suggest me how to do, since I have 1400 employees and their mail id, I'm getting their names in dropdown but when I'm selecting their names I need their mail id to display in the particular field......
$("#user_employee_id").change(function(){
$.ajax({
type: "GET",
url: "/User/emailcheck",
data: { email: user.email }
});
});
user_controller.rb
def emailcheck
#user = User.search(params[:email])
end
user.rb
def self.search(email)
if email
where('email = ?',email).first
end
end
Can any one tell how to get the email id when I click on the employee name? I need to get email id of that employee by default in email tab.
Try this:
$("#user_employee_id").change(function(){
var id = $(this).val();
$.ajax({
type: "GET",
url: "/User/emailcheck",
data: { id : id}
success : function( data ) {
$("#user_email").val(data);
},
error : function(err) {
}
});
});
user_controller.rb
def emailcheck
#user = User.find_by_id(params[:id])
respond_to do |format|
if #user.email.present?
format.json { render json: #user.email , status: :ok }
else
format.json { render json: "No mail id", status: :unprocessable_entity }
end
end
end
You can do this like
Chenge your js Code like:
$("#user_employee_id").change(function(){
var user_id = $(this).val(); #considering that your are setting id as a value of select field
$.ajax({
type: "GET",
url: "/user/emailcheck",
data: { id: user_id }
}).success(function(res){
$("#your_text_field_id").val(res.text);
});
});
and in your user_controller.rb
def emailcheck
user = User.find_by(id: params[:id])
if user.present?
render text: user.email
end
end

Angularjs: post data to rails server by service

I want send data from angularjs to rails server. For this, I have an angularjs service that I use GET,POST,DELETE,UPDATE method. I can use GET method, but for other method I cannot use, beacause I have to sent parameter to server, but I cannot do this.
record.js:
var app = angular.module('app');
app.controller('RecordCtrl',['$scope','Session','Records', function($scope, Session, Records){
$scope.records = Records.index();
}]);
recordService.js:
'use strict';
var app = angular.module('recordService', ['ngResource']);
//angular.module('recordService', ['ngResource'])
app.factory('Records', function($resource) {
return $resource('/api/record.json', {}, {
index: { method: 'GET', isArray: true},
create: { method: 'POST' }
});
})
.factory('Secure', function($resource){
return $resource('/api/record/:record_id.json', {}, {
show: { method: 'GET' },
update: { method: 'PUT' },
destroy: { method: 'DELETE' }
});
});
and I get data in rails server by below code:
class Api::V1::RecordController < Api::V1::BaseController
def index
respond_with(Record.all)
end
def show
#data = Record.find(params[:id]).to_json()
respond_with(#data)
end
def update
#data = Record.find(params[:id])
respond_to do |format|
if #data.update_attributes(record_params)
format.json { head :no_content }
else
format.json { render json: #data.errors, status: :unprocessable_entity }
end
end
end
def create
#data = Record.create(record_params)
#data.save
respond_with(#data)
end
def destroy
#data = Record.find(params[:id])
#data.destroy
respond_to do |format|
format.json { head :ok }
end
end
private
def record_params
params.require(:record).permit(:name)
end
end
I don't know how can I send method from angularjs controller to rails server. I try below code, but I don't successful:
Records.create(function() {
//"name" is the name of record column.
return {name: test3};
});
but I get below error in rails server:
Started POST "/api/record.json" for 127.0.0.1 at 2014-08-30 17:55:27 +0430
Processing by Api::V1::RecordController#create as JSON
How can I fix this problem? How can I send parameter to rails server?
I want send delete method to rails server. I know I have to send record.id to server, I use below type:
//type 1
var maskhare = { record_id: 4};
Secure.destroy(function(){
return maskhare.json;
});
//type 2
Secure.destroy(4);
but I get below error in server:
Started DELETE "/api/record" for 127.0.0.1 at 2014-08-30 19:01:21 +0430
ActionController::RoutingError (No route matches [DELETE] "/api/record"):
I fix correct url in recordService.js, but I don't know why request is send to before url again. Where is the problem?
It looks like you are successfully making a request, the last line there says that a POST request was made and went to the right controller and action.
The problem is strong parameters. You need to add name to the filtered parameters list.
private
def record_params
params.require(:record).permit(:secure, :name)
end
Also rails expects the parameters in the following format: { record: {name: 'something"} }
To fix your second problem
I would try to follow this recipe
Replace your code with this:
app.factory("Secure", function($resource) {
return $resource("/api/record/:id", { id: "#id" },
{
'show': { method: 'GET', isArray: false },
'update': { method: 'PUT' },
'destroy': { method: 'DELETE' }
}
);
});
and then
Secure.destroy({id: 4});
Keep in mind that if you add respond_to :json in your controller then you can omit the .json in the URLs. Like so:
class Api::V1::RecordController < Api::V1::BaseController
respond_to :json
...
end

calling a method with signature

I have a method with a signautre in rails:
def my_function(some_variable)
end
I call the method from jquery get function like this:
$.get('/controller/my_function', {data: mydata}, function(){
});
But I get an error because I need to send the argument also.
How can I do that?
You need to define an action in your controller and call your function from that action
def my_action
my_function(params[:data])
end
and your jquery script will be calling my_action
$.get('/controller/my_action', {data: mydata}, function(){
});
as #Henry pointed out - in your javascript code data: xxxx is HTTP parameters being sent from the browser to your rails controller action on the server, rails puts all HTTP parameters into the params hash, so if you had
var data = {
first_name: "Joe",
last_name: "Smith"
}
$.get('/controller/some_action', data, function() {
// ...
access those in the params hash on the server
def some_action
logger.debug params.inspect
# => { :first_name => "Joe", :last_name => "Smith", :action => "some_action" }
user.first_name = params[:first_name]
# ...
end

Resources