How to create POST Request in Ruby - ruby-on-rails

I have functionality where I need send delivery payload with static basic token and additional header.
scope = "xapi:read" # some require xapi:read, some require xapi:all
client_auth_header = "Basic <insert token here>"
client_version_header = "1.0.3"
client_site = "<Provided by client>"
I need to do this with post request
curl --request GET \
--url https://client-url/data/xAPI/agents \
--header 'Authorization: Basic XYZABC' \
--header 'X-Experience-API-Version: 1.0.3'
How do I write a post request in ruby ?
with something like this
client.post("/xAPI/statements", body: data.to_json, headers: { "Content-Type" => "application/json" })
what should I replace the client with ?

The httparty gem supports a very similar API to what you described here, with HTTParty.post.

Related

How to send url-encoded form data using Faraday's post method?

I'm trying to setup Faraday to make requests to a Twilio API. I can make the requests via Postman setting up the key/values in the request body as x-www-form-urlencoded data.
When I try to replicate the cURL I make on Postman in Rails I get an error as if the key/value pairs I send in the payload are not recognized
The following cURL request works in Postman:
curl --location --request POST 'https://api.twilio.com/2010-04-01/Accounts/TOKEN1234/Messages.json' \
--header 'Authorization: Basic AUTH_TOKEN==' \
--header 'Content-Type: application/x-www-form-urlencoded' \
--data-urlencode 'From=whatsapp:+5491112312312' \
--data-urlencode 'Body=Hello. Your order is on the way' \
--data-urlencode 'To=whatsapp:+541132132121'
My Faraday connector looks like this:
class Twilio::SubAccountConnector
attr_reader :sid, :auth_token, :phone, :api_url
def initialize(account)
#sid = account.twilio_configuration.sid
#auth_token = account.twilio_configuration.auth_token
#phone = account.twilio_configuration.phone
#api_url = "https://api.twilio.com/2010-04-01/Accounts/#{sid}/Messages.json"
end
def form_data
{
from: "whatsapp:+5491112312312",
body: "Hello. Your order is on the way",
to: "whatsapp:+541132132121",
}
end
def send_whatsapp_notification
connector.post do |req|
req.body = form_data
end
end
private
def connector(url = api_url)
Faraday.new(url: url) do |faraday|
faraday.request :basic_auth, sid, auth_token
faraday.request :url_encoded
faraday.response :json
faraday.adapter Faraday.default_adapter # make requests with Net::HTTP
end
end
end
This is the request body in the Faraday request:
request_body=
"{\"From\":\"whatsapp:+5491112312312\",\"Body\":\"Hello. Your order is on the way\",\"To\":\"whatsapp:+541132132121\"}"
I'm getting the following error in the response body, so I suppose I'm doing something wrong with the way I'm sending the payload as the key/value pairs are not recognized.
response_body={"code"=>21604, "message"=>"A 'To' phone number is required.", "more_info"=>"https://www.twilio.com/docs/errors/21604", "status"=>400}>
Am I missing something in the connector method so the payload is encoded correctly?
The issue is that the parameters should start with capital letters. Your Faraday request is otherwise correct, but your form_data method should look like:
def form_data
{
From: "whatsapp:+5491112312312",
Body: "Hello. Your order is on the way",
To: "whatsapp:+541132132121",
}
end

How to execute curl from rails application

Hi I am trying to create a payment module for my rails application with sum up. This is the rest api that they are providing I tried with RestClient but it is returing 400 bad request.
curl -X POST \
https://api.sumup.com/token \
-H 'Content-Type: application/x-www-form-urlencoded' \
-d 'grant_type=client_credentials'\
-d 'client_id=**Client_ID**'\
-d 'client_secret=**Client_Secret**'
This is what my restclient method looks like :
RestClient::Request.execute(
method: :post,
url: "https://api.sumup.com/token",
data: "grant_type=client_credentials&client_id=**CLIENT_ID**&client_secret=**Client_Secret**",
headers: { "Accept" => "application/json", "Content-Type" => "application/x-www-form-urlencode" }
)
Am I doing something wrong ?
You don't need to manually form encode the parameters which is a very likely source of errors.
RestClient.post(
"https://api.sumup.com/token",
{
grant_type: "client_credentials"
client_id: "**CLIENT_ID**"
client_secret: "**Client_Secret**"
},
{
accept: "application/json",
content_type: "application/x-www-form-urlencode"
}
)

curl post request in rails controller

I want to convert this post request written in curl (GoPay payment gateway) to my Rails application:
curl -v https://gw.sandbox.gopay.com/api/oauth2/token \
-X "POST" \
-H "Accept: application/json" \
-H "Content-Type: application/x-www-form-urlencoded" \
-u "<Client ID>:<Client Secret>" \
-d "grant_type=client_credentials&scope=payment-create"
I am trying to do in my rails controller by using a gem rest-client. I've done something like this and was modifiying many times but couldn't make it works:
RestClient::Request.execute( method: :post,
url: "https://gw.sandbox.gopay.com/api/oauth2/token",
"#{ENV['GOPAY_CLIENT_ID']}": "#{ENV['GOPAY_CLIENT_SECRET']}"
data: "grant_type=client_credentials&scope=payment-create"
)
How I can convert the curl post request for the rest-client (or similar)?
EDIT: It is showing a status code 409: Conflict with no further information
EDIT1 - rgo's modified code works, thank you:
RestClient.post "https://#{ENV['GOPAY_CLIENT_ID']}:#{ENV['GOPAY_CLIENT_SECRET']}#gw.sandbox.gopay.com/api/oauth2/token",
{ grant_type: 'client_credentials', scope: 'payment-create'},
content_type: :json, accept: :json
I'm not a RestClient user but after reading the documentation[1] I think I transformed your cURL request to RestClient:
RestClient.post "http://#{ENV['GOPAY_CLIENT_ID']}:#{ENV['GOPAY_CLIENT_SECRET']}#https://gw.sandbox.gopay.com/api/oauth2/token",
{ grant_type: 'client_credentials', scope: 'payment-create'},
content_type: :json,
accept: :json
As you can see I pass the credentials in the URL because is a basic authentication. Data(grant_type and scope) is passed as hash and then converted to JSON. Then we set rest client to send and receive JSON.
I hope it helps you
[1] https://github.com/rest-client/rest-client#usage-raw-url
You didn't mention exactly what doesn't work or what error you're seeing. However, the -u option for curl is used to pass the username and password for basic authentication.
The equivalent for RestClient is to use the user and password options e.g.
RestClient::Request.execute(
method: :post,
url: "https://gw.sandbox.gopay.com/api/oauth2/token",
user: "#{ENV['GOPAY_CLIENT_ID']}",
password: "#{ENV['GOPAY_CLIENT_SECRET']}"
data: "grant_type=client_credentials&scope=payment-create",
headers: { "Accept" => "application/json", "Content-Type" => "application/x-www-form-urlencode" }
)

curl request in ruby RestClient

The fastbill API states in its docu to make this curl request in order to receive information:
curl -v -X POST \
–u {E-Mail-Adresse}:{API-Key} \
-H 'Content-Type: application/xml' \
-d '{xml body}' \
https://my.fastbill.com/api/1.0/api.php
Using RestClientI tried to translate this into a ruby like request:
How I read this:
- make a post request to https://my.fastbill.com/api/1.0/api.php using basic authentification and stating the content type in the header, correct?
Now this would be a resource based request in RestClient like this:
First I authenticate:
resource = RestClient::Resource.new( 'https://my.fastbill.com/api/1.0/api.php', 'my#email.de', 'API-KEY-XXXXX' )
which works and authorises me.
then putting my request in:
xml = '<?xml version="1.0" encoding="utf-8"?><FBAPI><SERVICE>customer.get</SERVICE><FILTER/></FBAPI>'
resource.post xml, content_type: 'application/xml'
It always returns 400 and I don't know what else to do here.
Also how would json work here?
resource.post param1: 'value', content_type: 'json'
would be obvious.
You can utilize the Restclient::Request.execute. 400 errors typically indicate that the request was not understood by the recipeint. This could be caused by the headers or malformed data. You may need to add the accept header. Try the example below
require 'rest_client'
RestClient::Request.execute(
method: :post,
user: 'api_user#example.com',
password: 'pass123',
url: "https://example/users.json",
headers: {content_type: :json, accept: :json},
payload: { 'user' => { 'name' => 'John Doe', 'email' => 'john.doe#example.com'} }.to_json,
)
You can find a detailed list of options here
$url="https://my.fastbill.com/api/1.0/api.php";
$curl = curl_init();
curl_setopt($curl,CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
$result = curl_exec($curl);
curl_close($curl);
print_r(json_decode($result));

Convert curl command to httparty

I am trying to add merge field in Mailchimp V3 list with HTTParty but not able to convert curl to HTTParty format.
Curl Request format which is working fine :
curl --request POST \
--url 'https://usxx.api.mailchimp.com/3.0/lists/17efad7sd4/merge-fields' \
--user '12:d1c1d99dr5000c63f0f73f64b88e852e-xx' \
--header 'content-type: application/json' \
--data '{"name":"FAVORITEJOKE", "type":"text"}' \
--include
Httparty format with error API key missing
response = HTTParty.post("https://us12.api.mailchimp.com/3.0/lists/17efad7sde/merge-fields",
:body => {
:user => '12:d1c1d99dr5000c63f0f73f64b88e852e-xx',
:data => '{"name":"FAVORITEJOKE", "type":"text"}',
:include => ''
}.to_json,
:headers => { 'Content-Type' => 'application/json' } )
I also try it without include option but not working
There are several errors in your code.
curl user is the basic auth user, but you are passing it in the payload of the request
data is the payload, instead you are passing it as a node in your payload and then you double serialize it
include makes no sense there, it's not a payload item
This should be the correct version. Please take a moment to read the HTTParty and curl documentation and understand the differences.
HTTParty.post(
"https://us12.api.mailchimp.com/3.0/lists/17efad7sde/merge-fields",
basic_auth: { username: "12", password: "d1c1d99dr5000c63f0f73f64b88e852e-xx" },
headers: { 'Content-Type' => 'application/json' },
body: {
name: "FAVORITEJOKE",
type: "text",
}.to_json
)

Resources