I have a REST server that takes a query string in the request body of a GET statement.
It's similar to the Parse REST api that does the same. As seen in the curl statement below.
curl -X GET \
-H "X-Parse-Application-Id: ${APPLICATION_ID}" \
-H "X-Parse-REST-API-Key: ${REST_API_KEY}" \
-G \
--data-urlencode 'where={"playerName":"Sean Plott","cheatMode":false}' \
https://api.parse.com/1/classes/GameScore
My question is: How do I send a Backbone fetch (essentially a -X GET) with a data string.
Ive tried the following;
fetch: function(options) {
options = _.extend({data: 'Active is true' }, options);
return Backbone.Collection.prototype.fetch.apply(this, arguments);
}
Currently, that appends the string on the URL as parameters as such
http://restserver.com/collection/Customer?Active%20eq%20true
In your collection class, implement the url property as a function that returns the URL path plus the query string you want. The query string can be built up from properties stored on your collection instance like collection.playerName, etc. This pattern works well for a search query string type use case such as yours.
Related
I have a complex json request that I'd like to POST to an api but I can't find the proper way to do this inside Convertigo Studio. Could anyone please indicate me the best way to do this?
Here is the request I'm send through curl that gives me the results. These result will be used by the front to display data.
curl -k -H "Accept: application/json" --compressed -XPOST https://myserverurl/api/search -d #- << EOF
{
"api-key":"somekey",
"usage":"someusage",
"criteria":{
"timestamp":{"from-to":{"date-pattern":"yyyy/MM/dd-HHmmss","from":"2019/07/28-000000","to":"2019/08/27-235959"}},
"timestamp-field":"timestamp",
"metric":"*",
"filter":{
"and":
[
{"eq":{"attribute":"type","value":"sometype"}},
{"simple-query":{"query":"_exists_:city"}},
{"neq":{"attribute":"status","value":"1"}}
]
}
},
"info":"someinfo",
"size":10000,
"mode":"last-hits",
"format":{"tabular":{"columns":["col1", "col2","col3"],
"last-hits-columns":["name"],"order-by":[{"name":"name","direction":"ASC"}]},
"timestamp":{"date-pattern":"dd/MM/yyyy HH:mm:ss"}},
"index":"someindex",
"last-hits-count":"1"
}
EOF
I now would like to transpose that into a Convertigo approach using the proper connector and transactions but so far I'm hitting a wall. Any help is appreciated.
update: So I've managed to contact the API, i.e. reproducing the first part of the curl, by implementing a HTTP_Connector and then a HTTP_Transaction. The server is answering in the expected way.
Now what I can't do is posting the json string. I've tried implementing a http_single_variable which default value is that json string but it doesn't work, I get the following error:
HTTP result {ContentType: application/json, Length: 277}
{"error":{"request":"http://localhost:8550/api/search","message":"Unexpected character ('H' (code 72)): expected a valid value (number, String, array, object, 'true', 'false' or 'null')\n at [Source: java.io.InputStreamReader#6c195833; line: 1, column: 2]","target":"/search"}}
The error seems to be coming from the header, which has been defined as Accept, application/json. When I remove it I get a HTTP 500 Error from the server.
To post a JSON body in a Convertigo request you have to add a variable "__body" to your transaction:
HTTP single-valued variable
If your API returns a JSON response, you should use a JSON_HTTP_transaction instead of your HTTP_Transaction transaction.
Set "HTTP verb" property transaction to POST and "HTTP headers" property to "Content-type, application/json".
The value of the __body variable is set in a sequence by a Sequence_JS step like this:
var data = {
"param1": "value1",
"param2": "value2",
...
};
Then, use a jElement step to transform "data" to a JSON string source:
JSON.stringify(data)
in "Expression" property.
Next step is the Call of your transaction. In the __body Source point to the jElement text.
Here is a link to a Convertigo (7.5.7+) sample:
useBody.car
Hope that Helps.
I'm facing a problem with complex http request via cURL.
I'm building REST API with NODEjs, using Express routers and Multer middleware to handle multiple body data and files.
My endpoint route 127.0.0.1/api/postData
expects:
json data with fields, one of which is array of json objects (I'm having nested mongoose schema) and 2 named images (png/jpg).
I need to send Post request via cURL with the following 5-object data structure:
name String
description String
usersArray Array of json objects like: [{"id": "123"}, {"id": "456}]
imgIcon Png/Image providing /path/to/imageIcon.png
imgHeader Png/Image providing /path/to/imageHeader.png
I've read a lot of threads on stackoverflow, but all of them are answers to a particular singular problem, one thread about curl post images, another cURL post arrays, but not altogether.
I've tried REST API test tools like POSTMAN and DHC (google chrome), and there everything's fine except for arraysArray field
I used the fields like:
usersArray[0] {"id": "123"}
usersArray[1] {"id": "456"}
But validation didn't pass, cuz the json object value is parsed somehow incorrectly.
So I decided to put everything in cURL script.
I tried to write my cURL request in following way:
#!/bin/bash
curl -H 'Content-Type: application/json'
-H 'Accept: application/json' -X POST
-F "name=Foo Name Test"
--data '[{"id": "a667cc8f-42cf-438a-b9d8-7515438a9ac1"}, {"id": "7c7960fb-eeb9-4cbf-9838-bcb6bc9a3878"}]'
-F "description=Super Bar"
-F "imgIcon=#/home/username/Pictures/imgIcon.png"
-F "imgHeader=#/home/username/Pictures/imgHeader.png" http://127.0.0.1:7777/api/postData
When I run my cUrl script in bash
./postData
I got this:
$ Warning: You can only select one HTTP request!
You can help with:
1) Any Idea how to write such a complex HTTP REST request in cURL
2) Or with suggestion of tools (like DHC, POSTMAN) to solve this complex http request.
3) or with any idea how to write this request with the help of request.js node http request library.
Thank you all in advance for all answers, thoughts and ideas!!
Regards, JJ
You can try POSTMAN or google chrome ext app for REST api testing DHC.
But you should use multidimensional array instead of using JSON objects as a value, that can cause problem during validation.
Try this in DHC:
|FIELD| |VALUE|
name 'Some name'
description 'Some description'
usersArray[0][id] 89a7df9
usersArray[1][id] dskf28f
imgIcon (select type of field "file" and upload image)
imgHeader (select type of field "file" and upload image)
The way it works above is:
usersArray[0][id] specifies multidimensional array and places on position 0 an object {} with key "id" and value which you sepcify in value part.
So usersArray[0][id] "123" creates [{"id": 123}]
usersArray[1][id] "456" adds another element to array, so array becomes: [{"id": "123"},{"id": "456"}]
Sometimes you would want to use shell+curl to make RestAPI Calls, and you may want to pass complex json as data. And in case you want to use variables and create that data during execution time, you probably end up using lot of escape characters () and code would look ugly. I was doing the same thing as well, Windows powershell has a method to convert Dictionary|Associative Array to JSON which really helps in that realm but looked for something similar but couldn't find anything. So this is a sample code that would help:
#!/bin/Bash
# Author Jayan#localhost.com
## Variable Declaration
email="jayan#localhost.com"
password="VerySecurePassword"
department="Department X"
## Create JSON using variables in Bash
creds="{^email^:^${email}^, ^password^:^${password}^}"
department="{^department^:^${department}^}"
authdata_crippled="{^Authenticate^:[${creds},${department}]}"
# Replace ^ with "
authdata_json_for_RestAPI_Call=$(echo ${authdata_crippled}|tr '^' '"')
# Testing syntax
# Get "jq": yum install jq OR https://stedolan.github.io/jq/
echo ${authdata_json_for_RestAPI_Call} | jq .
# Then you make API call using curl
# Eg:
curl http://hostname:port/right/endpoint/for/api/Authenticate -X POST --header "Content-Type:application/json" -d ${authdata_json_for_RestAPI_Call} --cookie-jar cookie.data
Hope this helps someone.
I'm trying to test AngularJS's post method out, but so far I have not figured out how to get it work.
Here is my code snippet.
parameter = { categoryName: '' }; <- just a dummy parameter purposely set to '' for testing purposes
this.httpService({
method: 'POST',
url: '/svc_templates/svc_fetch_category.php',<- Just echoing some JSON string.
data: parameter
}).then(function (response) {
console.log(response);
The response I'm getting is shown below.
It seems that a call to the php file is going through, but the actual data(JSON) is not returning for some reason...
Could anyone help me out?
Make sure that the server .php file is actually working using curl e.g.:
curl -X POST -d #filename.txt http://example.com/svc_templates/svc_fetch_category.php --header "Content-Type:application/json"
Where filename.txt contains the JSON data you want to send.
I have a working curl call:
curl -X GET \
-H "X-Parse-Application-Id: XXXX" \
-H "X-Parse-REST-API-Key: YYYY" \
-G \
--data 'where={"number":1}' \
https://api.parse.com/1/classes/Day
How do I translate this into an angular $http call? I have tried every permutation I can think of, and it still retrieves every Day object. Base on the documentation, I expected the following to work:
$http({method: 'GET', url: 'https://api.parse.com/1/classes/Day',
data: {"where": {"number": 1}}});
EDIT:
I updated my code to use the Parse JavaScript SDK as recommended in the accepted solution. I installed it using bower:
bower install --save parse
In my app.js I initialize Parse:
Parse.initialize(parseAppId, parseJavascriptKey);
The controller code is a lot more verbose than what I had before, but does work correctly and provides more flexible querying:
var Day = Parse.Object.extend("Day");
var query = new Parse.Query(Day);
query.equalTo("number", currentDay); // Only retrieve objects matching currentDay
query.include('challenge,quote'); // Related objects
query.find({
success: function(results) {
console.log("Retrieved object with id: " + results[0].get('id'));
$scope.day = results[0];
$scope.$apply();
},
error: function(error) {
console.log(err);
}
});
While Wayne is 100% correct, We have decided to go a bit further and wrote a parse-angular seed project for developing web apps. It can be found here.
After you pulled it, do a npm install
As usual, cloud code should go into cloud/main.js,
express code: cloud/app.js
angular code: cloud/public/js/
Note that: You will need to change your AppId and AppKey in
config/global.json
cloud/public/js/app.js
Then you should have a nice parse-angular project set up and good to go.
If there's anything wrong, please feel free to open a pull request. :)
Instead of using $http you should be using the parse javascript api instead. https://parse.com/docs/js/guide
I have a function which does a HTTP GET request on Parse, using the code below. (I'm using AngularJs).
$http({ method: 'GET',
url: 'https://api.parse.com/1/classes/foo',
headers:{
"X-Parse-Application-Id": "MYPARSEAPPID",
"X-Parse-REST-API-Key": "MYPARSERESTAPIKEY",
"X-Parse-Session-Token": UserService.sessionToken,
},
params: {
where:{"toto":{"$gt":42}}
}
}).success(function(data, status) {
/* DO SOMETHING*/
}).error(function(data, status) {
/* DO SOMETHING */
});
I wrote this code using Parse' REST documentation (https://www.parse.com/docs/rest#queries-constraints)
which give this example (curl):
curl -X GET \
-H "X-Parse-Application-Id:..............." \
-H "X-Parse-REST-API-Key:.............." \
-G \
--data-urlencode 'where={"score":{"$gte":1000,"$lte":3000}}' \
https://api.parse.com/1/classes/GameScore
This is the result of the AngularJS request above seen through Chrome's Dev Tools:
where:{"toto":{}}
And this this the result of the same code, without the '$' character (it doesn't work, but the requet is sent as it should):
where:{"toto":{"gt":42}}
As you can see, the constraint disappears because of the '$' character.
I supposed angular doesn't let us use '$' as it is used for Angular properties/methods.
Any suggestion/ideas/example will be very helpful.
Edited:
I tried to stringify the params as RobH said, click here to look at the result seen through Chrome's Dev Tools.
The result of this query seems ignore completly the given contraints, even if the '$' caracter hasn't been striped. I found that someone else tried to stringify the params (How to pass parameters to $http in angularjs?), but according to the last comment, it "does not work ({method:'GET', url:'/search', stringifiedJsonData} is not a valid JavaScript literal)". I'm not sure about the relevance of this comment as I'm new at AngularJs and web in general.
Any other ideas ?