I am using the following cURL request to localhost which runs fine:
curl -u admin:e4d4face52f2e3dc22b43b2145ed7c58ce66e26b384d73592c -d "{\"jsonrpc\": \"2.0\", \"method\": \"feed.list\", \"id\": 1}" http://localhost/minifluxR/jsonrpc.php
But when I send the same request using Postman instead of cURL, I am getting:
{"jsonrpc":"2.0","id":null,"error":{"code":-32700,"message":"Parse error"}}
In Postman I used a GET request and sent the following as headers:
url:http://localhost/minifluxR/jsonrpc.php
username:admin
api_token:e4d4face52f2e3dc22b43b2145ed7c58ce66e26b384d73592c
method: feed.list
The following is the PHP function I am trying to trigger:
$server = new Server;
$server->authentication(array(
\Model\Config\get('username') => \Model\Config\get('api_token')
));
// Get all feeds
$server->register('feed.list', function () {
return Model\Feed\get_all();
});
Please help me to correct these errors.
When using cURL, the -u option (or --user) is used to supply the credentials for HTTP Basic authentication. This sets the Authorization header to contain the necessary data to authenticate with the server.
These steps apply to Postman's packaged app. For steps for the legacy app, view this of revision this answer.
To use HTTP Basic authentication as you were in your cURL command, click the Authorization tab and enter your credentials. Clicking Update Request will add the necessary Authorization header for you.
To submit the JSON data in the same way that you did with cURL, use a POST request, select raw under the Body tab, and enter your data like so:
To debug this I used Fiddler - a free web debugging proxy.
I used cURL's --proxy option to make it send its requests through Fiddler like so:
curl \
--proxy http://localhost:8888 \
-u foo:bar \
-d "{\"jsonrpc\": \"2.0\", \"method\": \"feed.list\", \"id\": 1}" \
http://localhost
Now that the request goes through Fiddler, I can select it from the session list, and use the "raw" inspector to see the raw request:
This shows me that the cURL is making a POST request with HTTP Basic authentication and application/x-www-form-urlencoded content. This type of data normally consists of keys and values, such as foo=bar&hoge=fuga. However, this cURL request is submitting a key without a value. A call to var_dump($_POST) will yield the following:
With a = at the end of the data (like so: {"jsonrpc": "2.0", "method": "feed.list", "id": 1}=) the var_dump will yield the following:
However, it seems that JsonRPC will use file_get_contents('php://input') in your case. This returns the data that was submitted with the request, including a =, if the data ends with it. Because it will try to parse the input data as a JSON string, it will fail if the string ends with a =, because that would be invalid JSON.
Using the FoxyProxy extension for Chrome, I created a proxy configuration for Fiddler (127.0.0.1:8888), which allowed me to easily debug the data being sent by Postman's POST request. Using x-www-form-urlencoded with a key of foo with no value, the data sent was actually foo=, which would result in your JSON string being invalid.
However, using "raw" input will allow for the specified data to be sent without a = being added to the end of it, thus ensuring the data is valid JSON.
Curl is using HTTP Basic authentication by default. Your headers set in Postman are something different. Try using Basic Auth in Postman. It is in top panel, you fill in username and password and authorization header will be generated.
Related
Here are two GET requests. The first one using CURL in php works, but the second one generated by an HTML form receives an error from the response server.
The first (working) is a GET request using CURL
1.
curl 'https://api.authy.com/protected/json/phones/verification/start' \
-d api_key=my_key\
-d via=sms \
-d phone_number=my_number\
-d country_code=my_code
The second (not working) is a GET request URL like one generated from an html form <form method='get'>
2.
https://api.authy.com/protected/json/phones/verification/start?api_key=my_key&via=sms&phone_number=my_number&country_code=my_code
The error message from the response server when using the second one is:
{"message":"Requested URL was not found. Please check http://docs.authy.com/ to see the valid URLs","success":false,"errors":{"message":"Requested URL was not found. Please check http://docs.authy.com/ to see the valid URLs"},"error_code":"60000"}
Question
What is the difference between second GET request compared to the CURL GET request? They look to me like they are identical.
According to the documentation at https://www.twilio.com/docs/verify/api/verification, you should use a POST request to use that API, and that is what the -d option of cURL does.
In your second call, you send a GET request, and according to the documentation and the error message, that is not successful
I am making a Chrome Extension that talks to a website via an api. I want it to pass information about a current tab to my website via a cors request.
I have a POST api request already working. It looks like this:
...
var url = "https://webiste.com/api/v1/users/sendInfo"
...
xhr.send(JSON.stringify({user_name:user_name, password:password, info:info}));
Its corresponding curl statement is something like this:
curl -X POST https://website.com/api/v1/users/sendInfo -d '{ username:"username", password:"password", info: "Lot's of info" }' --header "Content-type: application/json
But, this is not as secure as we want. I was told to mirror the curl command below:
curl --basic -u username:password <request url> -d '{ "info": "Lot's of info" }'
But, one cannot just write curl into javascript.
If someone could either supply javascript that acts like this curl statement or explain exactly what is going on in that basic option of the curl script I think that I could progress from there.
The curl command is setting a basic Authorization header. This can be done in JavaScript like
var url = "https://webiste.com/api/v1/users/sendInfo",
username = "...",
password = "...";
xhr.open('POST', url, true, username, password);
xhr.send(...);
This encodes the username/password using base 64, and sets the Authorization header.
Edit As arcyqwerty mentioned, this is no more secure than sending username/password in the request body JSON. The advantage of using the basic authentication approach is that it's a standard way of specifying user credentials which integrates well with many back-ends. If you need security, make sure to send your data over HTTPS.
curl is the curl binary which fetches URLs.
--basic tells curl to use "HTTP Basic Authentication"
-u username:password tells curl supply a given username/password for the authentication. This authentication information is base64 encoded in the request. Note the emphasis on encoded which is different from encrypted. HTTP basic auth is not secure (although it can be made more secure by using an HTTPS channel)
-d tells curl to send the following as the data for the request
You may be able to specify HTTP basic authentication in your request by making the request to https://username:password#website.com/api/v1/users/sendInfo
I have been asked to write a program that takes a list of numbers and sends a post to ms.4url.eu via JSON/HTTP Post in format:
{
"username":"a",
"password":"b",
"msisdn":"071231231234",
"webhook":"http://example.com"
}
it receives a JSON Response,
{
"status":"ok",
"id":"1234-1234-12344423-123123"
}
I have been told I can use ngrok for the webhook and I have to send a HTTP Response 200 within 1s.
I should receive a Webhook Response:
{
"id":"1234-1234-12344423-123123",
"msisdn":"071231231234",
"status":"unavaliable",
"error":"1b",
"errorDesc":"Abscent Subscriber"
}
How would I go about grabbing the data from the JSON response and Responding with a HTTP 200 in order to receive the second response with the data?
I can get the first response in curl but I am unable to get the webhook working to a php file using ngrok and HTTP response sent to request the main information in the second response.
Edited :
I have executed the curl command,
curl -H 'content-type: application/json' \
-d '{"username":"a", "password":"b", "msisdn":"07123123124","webhook":"http://example.com/"}' \
HTTPS://ms.4url.eu/lookup
of which I get the first response "status ok". I would like to know how to get the response(Json format) in php using http post to the URL and the using a webhook to respond with 1second with a http 200 response to receive the further information from the API URL.
I ended up using ngrok and viewing the Raw POST response and getting the JSON and viewing the Raw data I still had more code to do in order t make this question valid as there are too many points to answer.
I am using the codeigniter rest server api library.
When I enter http://localhost/RESTapi/api/question?X-API-KEY=XXX in Postman with the PUT method
I'm getting:
{
"status": false,
"error": "Invalid API key "
}
It works fine with GET method
How can I fix this issue?
I've seen some API's that do not look at the GET params if you make a POST or PUT request for credentials or are inconsistent in how they do it.
Really, credentials should go in headers either via the Authorize header or a custom one for many reasons like 'not logging credentials to access logs', but I digress.
In this case you can try:
Put (no pun) the X-API-KEY=XXX inside the body of the PUT just to see if this works
See if/how the library accepts the API key in a header
Looking at this library in particular (https://github.com/chriskacerguis/codeigniter-restserver), they do support the header X-API-KEY. This should be where you put the key for ALL requests--it's best practice not to pass them as url params.
Here's the commandline example using curl from their Github project.
curl -X POST -H "X-API-KEY: some_key_here" http://example.com/books
In PHP you can use curl to set header like this:
curl_setopt($ch, CURLOPT_HTTPHEADER, array('X-API-KEY: XXX'));
An API I'm trying to program to requires multipart/form-data content with the HTTP GET verb. From the command line I can make this work like this:
curl -X GET -H "Accept: application/json" -F grant_type=consumer_credentials -F consumer_key=$key -F consumer_secret=$secret https://example.com/api/AccessToken
which seems like a contradiction in terms to me, but it actually works, and from what I see tracing it actually uses GET. I've tried a bunch of things to get this working using PHP's cURL library, but I just can't seem to get it to not use POST, which their servers kick out with an error.
Update to clarify the question: how can I get php's cURL library to do the same thing as that command line?
which seems like a contradiction in terms to me, but it actually
works, and from what I see tracing it actually uses GET
Not exactly. curl uses a feature of the HTTP/1.1. It inserts additional field to the header Expect: 100-continue, on which, if supported by server, server should response by HTTP/1.1 100 Continue, which tells the client to continue with its request. This interim response is used to inform the client that the initial part of the request has been received and has not yet been rejected by the server. The client SHOULD continue by sending the remainder of the request or, if the request has already been completed, ignore this response. The server MUST send a final response after the request has been completed.
Since they are insisting on HTTP GET, then just encode the form elements into query parameters on the URL you are GETing and use cURL's standard get options instead of posting multipart/formdata.
-X will only change the method keyword, everything else will remain acting the same which in this case (with the -F options) means like multipart formpost.
-F is multipart formpost and you really cannot convert that to a query part in the URL suitable for a typical GET so this was probably not a good idea to start with.
I would guess that you actually want to use -d to specify the data to post, and then you use -G to convert that data into a string that gets appended to the URL so that the operation turns out to a nice and clean GET.