Ruby - Get request body from incoming http call - ruby-on-rails

I am receiving http requests to my rails application to a url /account/postback
The body of this incoming request contains some json that I need to retrieve, how can I do this in ruby?

The following should print the body of the request
routes.rb
map.connect 'account/:action', :controller => 'accounts'
accounts_controller.rb
class AccountsController < ApplicationController
def postback
puts request.body.read
end
end

If your HTTP call is using the POST verb you could alternatively use request.raw_post to retrieve the contents sent in the request's body.
Hope it helps!

Related

How to restrict request based on params in ruby on rails

I want to update my API to v5 (post /api/v5/registrations) and still want to support v1,v2,v3,v4. Under v5, I do not want process the create/update request if a params with registration[:secret_token] is missing from request body.
how to do this?
Invalid request= {:user=>{:name=>XYZ, :roll_number=>1}}
Valid Request: {:user=>{:name=>XYZ, :roll_number=>1, :secret_token=>"DSGASDFG34534"}}
Thanks in Advance
You can add following code in application_controller.rb
before_action :authorize!
private
def authorize!
head :forbidden unless params[:secret_token].present?
end

Any alternative to redirect_to in rails api only application?

I would like to redirect to another url in rails controller action. like
def action_name
redirect_to url
end
I know i can do it simply using the above method. But i want to redirect in only one action in all my application. because of this i don't want to include this in controller.
include ActionController::Redirecting
is there any other way to redirect to a uri in api only applications. Thanks.
You can use respond_with which will respond with a appropriate response depending on the request type and the status of the model you pass to respond_with.
def create
#thing = Thing.create(thing_params)
respond_with(#thing)
end
This will give 201 - Created status and a location header if the the request is successful and a 422 - Unprocessable Entity if the validations fail.
Alternativly you can use head to send a header only response with no body.
def action_name
head :not_found, location: url
end
Note that :not_found could be any appropriate HTTP status.
If your using Rails API:
Route your path, and take the params, and return:
redirect_to controller: "client", action: "get_name", params: request.query_parameters and return

Saving rails request to JSON/YML

I'm using service which sends Webhooks to my application. I want to write RSpec test for handling them. It's important to have this request exactly the same (remote caller IP, headers with encrypted content).
I tried to save request as json:
class WebhookController < ApplicationController
def some_callback
File.open('temp/request_example.json','w') do |f|
f.write request.to_json
end
end
end
so I could later do:
describe WebhookController do
subject { get :some_callback, JSON.parse(File.open('temp/request_example.json')) }
it 'does something' do;end
end
but unfortunately you cannot call request.to_json(request.to_json
IOError: not opened for reading). You can't either get directly to request.body or request.headers.
How to save such request for later usage in tests? Is there any gem for it?

Force Omniauth to use json for callback?

I'm attempting to integrate Omniauth into an API written in rails, to be used by an Android application. This means that I want to be able to handle the omniauth callback with JSON.
By default, Omniauth sends its callbacks to /auth/:provider/callback, is there a way that I can force Omniauth to instead send its callbacks to /auth/:provider/callback.json?
You can specify format in action where handling callback:
# in route.rb
match '/auth/:provider/callback' => 'authentications#create'
# in authentications_controller.rb
class AuthenticationsController < ApplicationController
def create
# your code here
respond_to do |format|
format.json { ... } # content to return
end
end
end
I managed to do that by inspecting the request object on my rails backend.
When I make the request on my app, I add data on the submition defining the format:
format: "json"
And the omniauth then makes the callback for
/auth/:provider/callback
Wich in my case matches
sessions#create
as an HTML request. But once there, if you look at your request object in rails, and search for the omniauth.params hash you'll see that one of the values there is the format passed on tha data of the initial request:
"omniauth.params"=>{"format"=>"json", "provider"=>"facebook", "code"=>"..."}
Its a mather of you searching for this "format"=>"json" and doing a render json as an answear.
I hope it solves your problem.
# app/controllers/users_controller.rb
def authenticate
#credentials = request.env['omniauth.auth']
render json: #credentials
end
# config/routes.rb
get '/auth/:provider/callback', to: 'users#authenticate', as: 'user_auth'
And then all requests made to /auth/:provider/callback will return a JSON response by default.

How to print response body to stdout/stderr on Rails

I would like to print out response body generated by my app to stdout/stderr for debugging purposes. The traffic is server-server so I cannot use client tools to get hold of http traffic.
There is a mention of puts #response.body in http://api.rubyonrails.org/classes/ActionDispatch/Response.html, however in my app controller #response is undefined. Is there a way for me to print response body to logs in my rails app, and if so, how?
Based on the answer given, did it like this:
after_filter :print_response_body, :only => [:index]
def print_response_body
$stderr.puts response.body
end
In your controller, try
after_filter do
puts response.body
end

Resources