0

I tried searching for an answer to this problem but I haven't found it, sorry if it's duplicated

I have a simple app with a website in REACT and java backend, where the site gets a json from the backend and shows something with it. The problem is when the backend returns an error message, for example a 503 http response with the following body:

{"status":503,"name":"InternalServerErrorException","message":"3rd party service is not available"}

The thing is, fetch() only gets information about the http status code when response.ok is false. I can't get a statusMessage or the json returned from the backend (I tried with response.body but is a locked stream, it seems I'm not able to read it)

The fetch code is:

handleErrors = (response) => {
    if (!response.ok) {
        throw Error(response.statusText);
    }
    return response;
};

submit = (form) => {
    this.setState({ response: null, loading: true, error: false });
    fetch(this.getUrl(form))
        .then(this.handleErrors)
        .then((clusterList) => {
            return clusterList.json();
        })
        .then(clusterJson => this.setState({response: clusterJson, loading: false}))
        .catch((e) => {
        console.log(e);
        this.setState({ error: true, loading: false, errorM: e.message});
    });
};

I tried several things I found in other posts and tutorials but nothing seems to work. And I can't make every error message into a different error code, i.e. there are many errors for "bad input" that differs on the message.

Is there any way to get the extra information of the error?

Pernoctador
  • 108
  • 8
  • Have you tried just rethrowing the entire error response? Seems the best way to set yourself up for maximum error data extraction later if you just pass along everything received. – Drew Reese Jan 01 '19 at 01:12
  • That doesn't help, I need the message to print what has gone wrong to the user. The error I get only has the status value – Pernoctador Jan 01 '19 at 03:29
  • Well, I meant if you can pass as much of the error response as possible then it's easier to later derive the error. I've sometimes worked with some APIs the return completely useless errors and I'm forced to provide some generic error anyway. TBH, you probably want user-friendly errors over mysterious error codes anyway, from a usability standpoint.. – Drew Reese Jan 01 '19 at 03:37
  • Yeah but I am at the end of the line in the website.That's where I need to read the error I'm getting and print it nicely for the user. – Pernoctador Jan 01 '19 at 03:51

2 Answers2

0

If response.status is not 2xx, get the error from response.body.

ram1
  • 6,290
  • 8
  • 41
  • 46
0

Welp, I found it. It had to be there somewhere on another question, but it wasn't too obvious (is not even the answer to the question, just one answer) The thread that has the answer is Retrieve data from a ReadableStream object?

The thing is, I was trying to read the body as an stream or returning the content like when the response.ok == true. I have no idea why all the other methods listed elsewhere didn't work. To my surprise, that answer also didn't work for the one who asked that question.

The final answer is:

handleErrors = (response) => {
    if (!response.ok) {
        response.json().then(body => this.setState({errorMessage: body.message}));
        throw Error(response);
    }
    return response;
};

submit = (form) => {
    this.setState({ response: null, loading: true, error: false });
    fetch(this.getUrl(form))
        .then(this.handleErrors)
        .then((clusterList) => {
            return clusterList.json();
        })
        .then(clusterJson => this.setState({response: clusterJson, loading: false}))
        .catch((e) => {
        this.setState({ error: true, loading: false});
    });
};

Happy new year!

Pernoctador
  • 108
  • 8