Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

reading Error responses #112

Closed
Realtin opened this issue Jan 12, 2017 · 16 comments
Closed

reading Error responses #112

Realtin opened this issue Jan 12, 2017 · 16 comments

Comments

@Realtin
Copy link

Realtin commented Jan 12, 2017

When an API Request fails my Server sends a response with an explanation like this:

{  
  "errors":[  
    {  
      "title":"can't be blank",
      "detail":"name - can't be blank",
      "id":null,
      "href":null,
      "code":"100",
      "source":{  
        "pointer":"/data/attributes/name"
      },
      "links":null,
      "status":"422",
      "meta":null
    }
  ]
}

if I catch the error from the promise I'll only get Error: Unprocessable Entry
is there a way I can access the error response somehow?

@egeriis
Copy link
Collaborator

egeriis commented Jan 16, 2017

You should be able to read the server response from the promise resolver. Is that not possible?

@egeriis
Copy link
Collaborator

egeriis commented Jan 16, 2017

I.e. readEndpoint('dummy').then(res => console.log(res))

@Nopzen
Copy link
Collaborator

Nopzen commented Jan 16, 2017

@egeriis i think @Realtin issue is in the .catch(error) not in the promise :) Am i right ?

@Realtin
Copy link
Author

Realtin commented Jan 16, 2017

So the snipped I posted is what I can see in the chrome dev tools in the Network Tab:
bildschirmfoto 2017-01-16 um 13 48 35

I have code like this:

createEntity(stuff)
.then(
  (res) => {
    console.log(res)
  },
  (error) => {
    console.log(error)
  });

but the error here doesn't have all this information like the one in the network tab.
bildschirmfoto 2017-01-16 um 13 56 21

I would love to somehow be able to access the "detail" part where it tells me what exactlty went wrong. I have no Idea where that is coming from. it is nowhere in the error I can get in the promise

@egeriis
Copy link
Collaborator

egeriis commented Jan 17, 2017

You're right, the response body is not exposed through catch. I had to look at the source to be reminded: https://github.com/dixieio/redux-json-api/blob/master/src/jsonapi.js#L122

I'm just curious about the use case. Because getting a 422 back from an API means there's a programming error. What value does that provide to the application you're building, to be able to read that response from the API?

@aldavigdis
Copy link

@egeriis This is not only a result of programming errors, but also covers problems with user input and form validations, which in this case are done on the server side.

In this case, a lot of form validation falls back on the server and with a rather complicated model structure, so it's not always feasible to perform client-side validation to prevent this. Also, JSON API conventions account for error objects being thrown as described at http://jsonapi.org/examples/#error-objects.

@Realtin
Copy link
Author

Realtin commented Feb 14, 2017

☝️ this is my co-worker by the way. sorry for the late reply.

@egeriis
Copy link
Collaborator

egeriis commented Feb 14, 2017

@stefanvignir @Realtin You're absolutely right, don't know why I didn't consider that 🙂

It does look like we're exposing the response though: https://github.com/dixieio/redux-json-api/blob/master/src/utils.js#L20

And I think I was a bit quick in my earlier reply, because it looks like all the detail is there, in your screenshot?

What are you missing from the body in the response object from your screenshot?

@Realtin
Copy link
Author

Realtin commented Feb 14, 2017

my first screenshot (in this comment: #112 (comment)) is from the Chrome Dev Tools (Network Section) this is the raw response that is coming in from the backend.

And the second one is the console.log in my promise where I log the whole response object that I get through redux-json-api
(both are the same request at the same time)

so the errors[i].detail which would be interesting to have access to inside the frontend is missing after the response goes through redux-json-api.
Something is happening to the response, so that it gets restructured at some point.

@Realtin
Copy link
Author

Realtin commented Feb 14, 2017

could it be that the error.body in the Javascript error object is not filled correctly because the errors that come from the backend are an array?

btw. I'm happy to try to work on a fix for that if we can pinpoint the problem.

@egeriis
Copy link
Collaborator

egeriis commented Feb 14, 2017

I am not sure what detail is supposed to be, but if you simply want to read the response body as a JavaScript object, I am pretty sure that you can do error.response.json().then(json => ...)

@egeriis
Copy link
Collaborator

egeriis commented Feb 14, 2017

error.response should simply be the response object. We don't modify it at all, but set in on the error object to add the ability to do exactly what you're asking for 🙂

@aldavigdis
Copy link

I am not sure what detail is supposed to be

The detail attribute is generally the actual human-readable error message, while the title attribute is more of a heading-level message.

The source pointer then points to the attribute related to the error, to make it possible to highlight the field relating to the error.

(Example: { "title": "Invalid attribute", "detail": "Postal code does not correspond to the region/state selected", "source": { "pointer": "/data/attributes/postcode" } })

@egeriis
Copy link
Collaborator

egeriis commented Feb 16, 2017

@stefanvignir Aah! You're referring to the JSON API spec.

Ok, so here's the deal: you can read the error response already. As you can see in utils.js we add the response object to the thrown error: https://github.com/dixieio/redux-json-api/blob/master/src/utils.js#L20

That means that you can view the response object through error.response. If you want the response body parsed as JSON, you can use response.json() which returns a promise.

You can read more about the response object here: https://developer.mozilla.org/en-US/docs/Web/API/Response

@egeriis egeriis closed this as completed Feb 16, 2017
@Realtin
Copy link
Author

Realtin commented Feb 16, 2017

just to update:

I was looking at the error.response from the beginning but when you look at it (screenshot above) there is no evidence that there is this JSON API Spec Errors Array hiding anywhere. I was missing the information about connecting it with a .json() and that this returns a new promise which ultimately returns what I needed.

so:

createEntity(stuff)
.then(
  (res) => {
    console.log(res)
  },
  (error) => {
    error.response.json().then((response) => {
        console.log(response);
      });
  });

this finally gives me access to the Error Array!

@egeriis do you think that would be nice to have in the documentation? I could make a PR on the Weekend for this if you think it would be helpful to others.

@egeriis
Copy link
Collaborator

egeriis commented Feb 21, 2017

@Realtin It has nothing to do with redux-json-api, it's a regular Response object. But it would definitely be useful to mention that we're passing the Response object to the error 🙂

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants