I am trying to redo my react rails app with gresql so that I can deploy it with heroku. So far everything is working fine except the fetch POST request. I am getting a 404 (Not Found) error and binding.pry isn't coming up in my terminal so I can't see from the controller.
I think it might have something to do with how it is sending back json with render :json. Before I was using respond_to do |format| format.json {.
import fetch from 'isomorphic-fetch';
export function saveData(rec) {
debugger
return function(dispatch){
return fetch(`/api/v1/charts`, {
credentials: "include",
method: "POST",
headers: {
'Accept': "application/json",
'Content-Type': "application/json",
},
body: JSON.stringify(rec)
})
.then(res => {
return res.json()
}).then(data => {
debugger
dispatch({type: 'ADD_CHART', payload: data})
})
}
}
module Api::V1
class ChartsController < ApplicationController
def index
#charts = Chart.all
render json: #charts, include: ["people", "weights"]
end
def create
binding.pry
#chart = Chart.create(chart_params)
render json: #chart, include: ["people", "weights"]
end
def destroy
Chart.find(params[:id]).destroy
end
private
def chart_params
params.require(:chart).permit(:id, :date, people_attributes: [:name, weights_attributes: [:pounds, :currentDate] ])
end
end
end
module Api::V1
class PersonsController < ApplicationController
def index
#persons = Person.all
render json: #persons, include: "weights"
end
def create
binding.pry
#person = Person.create(person_params)
render json: #person, include: "weights"
end
private
def person_params
params.require(:person).permit(:id, :name, weights_attributes: [:pounds, :currentDate])
end
end
end
module Api::V1
class WeightsController < ApplicationController
def index
#weights = Weight.all
render json: #weights
end
def create
binding.pry
e = Weight.where(:person_id => params[:person_id], :currentDate => params[:currentDate])
if !e.empty?
e.first.pounds = params[:pounds]
e.first.save!
#weight = e
else
#weight = Weight.create(weight_params)
end
render json: #weight
end
private
def weight_params
params.require(:weight).permit(:id, :pounds, :currentDate, :person_id)
end
end
end
class ApplicationController < ActionController::API
end
If you've declared resource routes for your charts, you need to change this line:
return fetch(`/api/v1/charts`, {
to:
return fetch(/api/v1/chart, {
As is, charts is likely triggering a POST to your index action.
Changing my fetch to the full url and removing credentials: "include" worked
import fetch from 'isomorphic-fetch';
export function saveData(rec) {
debugger
return function(dispatch){
var url = 'http://localhost:3001/api/v1/charts';
return fetch(url, {
method: "POST",
headers: {
'Accept': "application/json",
'Content-Type': "application/json",
},
body: JSON.stringify(rec)
})
.then(res => {
return res.json()
}).then(data => {
debugger
dispatch({type: 'ADD_CHART', payload: data})
})
}
}
Related
I am using Zapier to search some information in google sheets. I used Webhocks to send a GET to his server with a JSON information. The response of GET is an "OK" and I can't custom this.
So, they will execute a task, find what a I want and return a value, but the response must be a GET in my server, and I don't know how to intercept this response in my route.
I'm trying to study Rails Rack to intercept de request in my app, but I don't know how to send the response to the event that sent the first GET.
How is my middleware:
class DeltaLogger
def initialize app
#app = app
end
def call env
Rails.logger.debug "#{env['QUERY_STRING']}"
#status, #headers, #response = #app.call(env)
[#status, #headers, #response]
end
end
Thanks!
Example
So, to get the value returned from Zapier, I created two routes and a global class cache.
class Zapier
require 'httparty'
def initialize
#answer = ""
#id = 0
end
def request(uri, task)
last_event = Event.last
puts last_event.inspect
if last_event.nil?
last_id = 0
else
last_id = last_event.event_id
end
event_id = last_id + 1
Event.find_or_create_by(event_id: event_id)
result = HTTParty.post(uri.to_str,
:body => {id: event_id, task: task}.to_json,
:headers => {'content-Type' => 'application/json'})
#answer = ""
#id = event_id
end
def response(event_id, value)
if event_id != #id
#answer = ""
else
#answer = value
end
end
def get_answer
#answer
end
end
And my controller:
class ZapierEventsController < ApplicationController
require 'zapier_class'
before_action :get_task, only: [:get]
before_action :get_response, only: [:set]
##zapier ||= Zapier.new
def get
##zapier.request('https://hooks.zapier.com',#task)
sleep 10 #Wait for response
#value = ##zapier.get_answer
render json: { 'value': #value }, status:
end
def set
##zapier.response(#id, #value)
render json: { 'status': 'ok' }, status: 200
end
def get_task
#task = params["task"]
end
def get_response
#id = Integer(params["id"])
#value = params["value"]
end
end
Now i have to make a Task Mananger
I have implemented my own object creation logic by overriding the create action in a JSONAPI::ResourceController controller.
After successful creation, I want to render the created object representation.
How to render this automatically generated JSON API response, using the jsonapi-resources gem?
Calling the super method does also trigger the default resource creation logic, so this does not work out for me.
class Api::V1::TransactionsController < JSONAPI::ResourceController
def create
#transaction = Transaction.create_from_api_request(request.headers, params)
# render automatic generated JSON API response (object representation)
end
end
You could do something like this:
class UsersController < JSONAPI::ResourceController
def create
user = create_user_from(request_params)
render json: serialize_user(user)
end
def serialize_user(user)
JSONAPI::ResourceSerializer
.new(UserResource)
.serialize_to_hash(UserResource.new(user, nil))
end
end
this way you will get a json response that is compliant with Jsonapi standards
render json: JSON.pretty_generate( JSON.parse #transaction )
def render_json
result =
begin
block_given? ? { success: true, data: yield } : { success: true }
rescue => e
json_error_response(e)
end
render json: result.to_json
end
def json_error_response(e)
Rails.logger.error(e.message)
response = { success: false, errors: e.message }
render json: response.to_json
end
render_json { values }
I am building a react-native app with rails api. I have a players_controller with create, index, update actions. I can do all things(create, index, update) from postman. But when I tried form fetch request from react action. I could only index and create player model. On update I get this error in debugger console.
:3000/players/1:1 OPTIONS http://localhost:3000/players/1
XMLHttpRequest cannot load http://localhost:3000/players/1. Response
for preflight has invalid HTTP status code 404
in Rails my players_controller.rb
class PlayersController < ApplicationController
skip_before_action :verify_authenticity_token
respond_to :json
def index
#players = Player.find_by(player_id: params[:player_id])
player = Player.all
render json: #players
end
def create
player = Player.new(player_params)
if player.save
render json: player, status: 201
else
render json: { errors: player.errors }, status: 422
end
end
def update
player = Player.find(params[:id])
player.update(player_params)
if player.save
render json: player, status: 201
else
render json: { errors: player.errors }, status: 422
end
end
private
def player_params
params.require(:player).permit(:username, :profile_pic, :player_id)
end
end
In my react-native app I have action
export const profilePicUpdate = (player, profile) => (dispatch) => {
const obj = player;
obj.profile_pic = profile;
fetch(`http://localhost:3000/players/${player.id}`, {
method: 'PATCH',
headers: {
Accept: 'application/json',
'Content-Type': 'application/json',
},
body: JSON.stringify({
obj
})
}).then(() => {
dispatch({
type: 'PROFILE_PIC_UPDATE',
payload: profile
});
NavigatorService.navigate('Profile');
}).catch((error) => {
console.log('Error', error);
});
};
It is need to see your roues.rb file, but also maybe you need to add
gem 'rack-cors'
and set up it
Rails.application.config.middleware.insert_before 0, Rack::Cors do
allow do
origins '*'
resource '*',
headers: :any,
methods: [:get, :post, :put, :patch, :delete, :options, :head]
end
end
in config/initializers/cors.rb
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
In my ruby on rails code I want to send back json response to client. Since I am new to ruby on rails I do not know how can I do this. I want to send error = 1 and success = 0 as json data if data does not save to database and if it successfully saves that it should send success = 1 and error = 0 Please see my code below
here is my controller
class ContactsController < ApplicationController
respond_to :json, :html
def contacts
error = 0
success = 1
#contacts = Contact.new(params[:contact])
if #contacts.save
respond_to do |format|
format.json { render :json => #result.to_json }
end
else
render "new"
end
end
end
here is my javascript code
$('.signupbutton').click(function(e) {
e.preventDefault();
var data = $('#updatesBig').serialize();
var url = 'contacts';
console.log(data);
$.ajax({
type: 'POST',
url: url,
data: data,
dataType: 'json',
success: function(data) {
console.log(data);
}
});
});
There are tons of other elegant ways, but this is right:
class ContactsController < ApplicationController
def contacts
#contacts = Contact.new(params[:contact])
if #contacts.save
render :json => { :error => 0, :success => 1 }
else
render :json => { :error => 1, :success => 0 }
end
end
end
Add also a route to routes.rb. If you need to use html response you have to include respond_to do |format|.
You have to adjust your routes to accept json data
match 'yoururl' => "contacts#contacts", :format => :json
Then it will work