Processing fetch response - JS - javascript

I have the response after GET-request with fetch. I know that this response will return an Array. When I process it with .json() - everything is fine. But when I try to process same response with .formData()- it fails.
Here's the code:
fetch(fullPath)
.then(response => response.json())
.then((allData) => {
console.log(allData);
})
.catch((e) => console.log(e));
same one with response.formData() doesn't work.
So the question is - why we are not able to process the promise in first "then" with .formData() if the off. doc says that formData() is also acceptable method for extracting a body from the response ?

The formData() method will return an error if the response is not having the multipart/form-data type. It should have key=value entries. See this question where someone asks about designing a response with that format.
Something similar happens if you call the json() method on a response that is not valid JSON: that also triggers an exception.
Since multipart/form-data is rarely used as response content type, the formData() method is not often used either. The documentation on MDN mentions it has some use for service workers:
Note: This [method] is mainly relevant to service workers. If a user submits a form and a service worker intercepts the request, you could for example call formData() on it to obtain a key-value map, modify some fields, then send the form onwards to the server (or use it locally).

Related

How to fetch dynamic json with respond.json function using javascript [duplicate]

I am trying to use fetch api to bring back some data, however am unable to map it to the console once I have retrieved it.
fetch('http://jsonplaceholder.typicode.com/users', {
method: 'GET'
}).then(function(response) {
console.log(response)
response.forEach(i => console.log(i.name));
}).catch(function(err) {
console.log(`Error: ${err}` )
});
The error i get is
response.map is not a function
so I tried to parse the response,(ie var data=JSON.parse) which did not work, with the error
SyntaxError: Unexpected token o in JSON at position 1"
Interestingly, when doing the same thing with a XMLHttp request, I was required to parse it, so I would also be interested to know why the difference between these two methods of retrieving the data.
If anyone could point me in the right direction, I would be really grateful.
The Fetch API returns a response stream in the promise. The response stream is not JSON, so trying to call JSON.parse on it will fail. To correctly parse a JSON response, you'll need to use the response.json function. This returns a promise so you can continue the chain.
fetch('http://jsonplaceholder.typicode.com/users', {
method: 'GET'
})
.then(function(response) { return response.json(); })
.then(function(json) {
// use the json
});
Understanding promises is key to using the fetch API.
At the time you're trying to parse your response and loop through it, the response is actually just a promise. In order to utilize the contents of the actual response from the request, you'll have to do some promise chaining.
fetch('http://jsonplaceholder.typicode.com/users').then(function(response) {
// response.json() returns a promise, use the same .then syntax to work with the results
response.json().then(function(users){
// users is now our actual variable parsed from the json, so we can use it
users.forEach(function(user){
console.log(user.name)
});
});
}).catch(err => console.error(err));
It appears that you might be accessing the json incorrectly. You could try calling response.json() instead.
fetch('http://jsonplaceholder.typicode.com/users', {
method: 'GET'
}).then((response) => {
response.json().then((jsonResponse) => {
console.log(jsonResponse)
})
// assuming your json object is wrapped in an array
response.json().then(i => i.forEach(i => console.log(i.name)))
}).catch((err) => {
console.log(`Error: ${err}` )
});
This example is structured to match your example, but ideally, you would return response.json() on that first .then block and proceed on the next block. Here is a similar example that proceeds on the next block.
In your particular case, you can view the Fetch API as a json aware wrapper for "XMLHttpRequest"s. Main differences being that the Fetch API is simpler, functional-like, and has convenience methods. David Walsh does a reasonable comparison in his blog post, which I recommend you take a look at. Plain "XMLHttpRequest"s just pass you whatever string was sent back from the server, it has no idea it could be JSON, and thus leaves it to the user to parse the response whatever way they see fit.

How to access data from "Passthrough" object returned after API call?

I am sending a fetch request with node-fetch to the following url: http://fantasy.premierleague.com/api/bootstrap-static/ in order to get back some JSON-data. Accessing the URL in the browser, or sending a get-request with postman both returns the expected JSON data.
However, when i send the request from node, I get back an object that I do not know how to extract the data from (pics below).
I am not very experienced with node but I have made successful API calls before. Usually parsing the response with response.json() or JSON.parse(response) or response.body or response.toString() or some combinations of those have worked for me. I am half familiar with buffers and streams, but not confident and the solution might be related to those, however I cannot seem to figure it out.
I get som different errors and objects depending on what I try. I have tried using fetch and just plain http requests from node.
This call:
Returns this:
If I do JSON.parse(response) i get the following error:
Response.body looks like this:
Fetch returns a response stream as mentioned here in the answer to a similar question
You can read data in chunks and add the chunk to array and then do whatever you need to do with that data. A simpler approach would be to use npm request package. Here's an example.
const request = require('request');
let options = {json: true};
const url = 'http://fantasy.premierleague.com/api/bootstrap-static/'
request(url, options, (error, res, body) => {
if (error) {
return console.log(error)
};
if (!error && res.statusCode == 200) {
console.log(body);
// do something with JSON, using the 'body' variable
};
});

Javascript Fetch API equivalent in Java for Http requests?

I am currently learning about Threads in Java. I wanted to know what the standard protocol would be when making Http Requests in Java that would be similar to the code I have below, which uses Javascript Fetch API and asynchronous programming. For example, if I was using the Fetch API in Javascript to first make a GET request to grab some data from a REST endpoint that I would later use to make a POST request (as seen in the code below), I would need to use a Callback function or Promise (like below) to wait until that first request has retrieved its data for the second request to then proceed. Obviously, if I did not use Promises or nest the second Http POST in the first Fetch method (GET) below, and wrote two separate Fetch API calls (one for GET, one for POST, sequentially one after other aka top-to-bottom), both calls would "fire-off" simultaneously and the second POST request wouldn't have the data it needs to make a successful POST.
const myHttpGETandPOSTmethod = () => {
// First Http request goes here
fetch('http://example.com/movies.json', {
method: 'GET',
headers: // Some headers here,
})
.then(response => response.json())
.then(data => {
console.log(data))
// Nest the second Http request inside here. It only runs after 1st request completes
return fetch('http://example.com/movies.json', {
method: 'POST',
headers: // Some headers here,
body: JSON.stringify(body);
})
.then((response) => response.json())
.then((data) => {
console.log('Success:', data);
})
.catch((error) => {
console.error('Error:', error);
});
})
}
So then, if I were using something like the Apache HttpClient https://hc.apache.org/httpcomponents-client-4.5.x/quickstart.html library in Java, would the standard procedure be to "spin-up" another Thread (besides the main thread) to execute the GET request and then do a thread.join() such that after the first thread completes, then the second request can fire-off its own Thread?
Would I need to use a Callable instead of Runnable so that I can save the HttpEntity data response of the first GET request?
I guess I'm just trying to understand the best way to implement the scenario I posed above regarding an HTTP GET request that is needed to make a subsequent POST request, while both fires asynchronously such that they do not block the main thread.
You can make a basic GET request using the apache Http Library as such (POST is also very similar):
CloseableHttpClient httpclient = HttpClients.createDefault();
HttpGet httpGet = new HttpGet("http://targethost/homepage");
CloseableHttpResponse response1 = httpclient.execute(httpGet);
try {
System.out.println(response1.getStatusLine());
HttpEntity entity1 = response1.getEntity();
// Save the response body to a string
String body = EntityUtils.toString(entity1, StandardCharsets.UTF_8);
System.out.println(body);
EntityUtils.consume(entity1);
} finally {
response1.close();
}
Or am I on the wrong approach here and looking at this incorrectly? I believe the Http library in Apache offers both synchronous and asynchronous Http calls? or should I be using a newer library for Http in Java?

Ionic 2 : Get the header of a response in http request

I want to have some information about the response when I request an API with http in Ionic 2 / Angular 2.
Informations like : response time, response size ... ect.
I use this code :
let url : "[myUrl]";
this.http.get(url).map(res => res.json()).subscribe(res => {
console.log(res);
});
I want to get the response header.
Someone know how to do that ? :)
this.http.get(url).map(res => {
console.log(res.headers); // Print http header
return res.json();
}).subscribe(res => {
console.log(res);
});
Angular Http request returns an Observable which contains all the information the server has passed. So you can access headers from the response as res.headers. To obtain the size of the response body you can use,
res.headers.get('Content-Length')
assuming this is present in the headers. So it depends on the information the response carries rather not what angular provides.
Response time information depends on what exactly you are looking for. For server response time in node.js you can use this package. Then in response , response time can be obtained with
res.headers.get('X-Response-Time')
If you want the total response time (including the network delay ) you will have use JavaScript timer and find the time difference between request and response.
So the information you are looking for mainly relies on the server response rather than angular. And beware of CORS in browser ( Access-Control-Expose-Headers in response header ) . You can understand more about headers here. Hope it helps.
You can. In the map function you can get the all the information regarding HTTP call. You can do whatever you want with the result (I've added only a console.log)
this.http.get(url).map(res => {
console.log(res); // Print http details
return res.json();
}).subscribe(res => {
console.log(res);
});

Using fetch() Webapi

I am trying to see how browser's native webapi fetch() api works. So far I have this: Sample-Code and it works fine. But what I don't understand why is it streaming string which I have to convert to a JSON? I am not sure why would anybody even need to stream a JSON as string through a REST API? I am pretty sure I am missing something here but I am not sure how I should tell fetch() to get the response as JSON and not as a ReadableByteStream which I have to convert to a string and parse it for a JSON.
My Question is this,
Why is a string being streamed here?
How do I tell fetch() to fetch my response as text or json so that I can do response.json() or response.text() as mentioned in the docs? (FYI I tried adding a header object and creating a Header instance and passing it to fetch() neither changed my response.
All you need to do is call
fetch("https://api.github.com/users/ajainarayanan").then(res => res.json());
Here is some modified code the has the same result
fetch("https://api.github.com/users/ajainarayanan")
.then(res => res.json())
.then(res => console.log('Profile: ', JSON.stringify(res, null, 2)));
Apparently I have to do response.json() in one then handler and have the actual value in subsequent then handlers. Update-code. What I didn't realize was response.json() returned another Promise which I should handle like a promise. So console.log(response.json()) will naturally just console log a JSON object instead of my actual json. Thank your #aray12 for you answer. I didn't realize the answer until I realize .json() returned a promise.
PS: Adding this as an answer as I couldn't add this in comments.

Categories