What is dispatch(..).unwrap() in redux-toolkit?
Asked Answered
L

6

7

From a redux tutorial:

const onSavePostClicked = async () => {
  if (canSave) {
    try {
      setAddRequestStatus('pending')
      await dispatch(addNewPost({ title, content, user: userId }))
        .unwrap()
    } catch (err) {
      console.error('Failed to save the post: ', err)
    } finally {
      setAddRequestStatus('idle')
    }
  }
}

As I understand dispatch(addNewPost({ title, content, user: userId })) will return a promise like that:

state: "fulfilled"

result: fulfilled action object

and dispatch(addNewPost({ title, content, user: userId })).unwrap() will also return a promise.

So what is the difference between the promise without and with unwrap?

state: "fulfilled"

result: ?
Loidaloin answered 21/3, 2023 at 16:44 Comment(2)
It is specific to redux's createAsyncThunk method. .unwrap() isn't a native API on Promise's prototype, redux adds this to the promise themselves. See redux-toolkit.js.org/api/…Mantooth
More details about this code are explained here: youtu.be/93CR_yURoII?t=1647Cawthon
D
8

dispatch(addNewPost({ title, content, user: userId })) will resolve to the latest action that has been dispatched by that thunk.

With .unwrap(), it will resolve to the value of the fulfilled action, or throw on a rejected action.

The idea here is that you should be able to dispatch an asyncThunk without having to catch it every time, but only if you really want to write more logic based on it.

Devereux answered 21/3, 2023 at 23:16 Comment(3)
but "catching" in javascript is just about console.log(err) usually. And so at that point I see no reason to logging or not catching at all since you would see the error anyway (if one was thrown)Elisa
@Elisa catching is almost never about logging, console.log is just something you see in examples and code that copy-pasted these examples without thinking.Devereux
I mean if you are in catch block it means you have an error and oftentimes there is nothing you can do but to just log it so that you know what that error is. Unless you 1) know the error beforehand and 2) have resolution for it (in context of frontend that could be updating UI with error message), there is not much you can do.Elisa
W
7

You can get the official document about the .unwrap usage case.

createAsyncThunk handles any errors internally, so that we don't see any messages about "rejected Promises" in our logs. It then returns the final action it dispatched: either the fulfilled action if it succeeded, or the rejected action if it failed.

However, it's common to want to write logic that looks at the success or failure of the actual request that was made. Redux Toolkit adds a .unwrap() function to the returned Promise, which will return a new Promise that either has the actual action.payload value from a fulfilled action, or throws an error if it's the rejected action. This lets us handle success and failure in the component using normal try/catch logic.

enter image description here

In one world, It help you can catch the error which has been wraped by createAsyncThunk in your components

Hope it can helps you

Whitt answered 18/3 at 10:8 Comment(0)
D
3

In your e.g,

If addNewPost succeeds:

  • It will pass through unwrap() without any issues

If addNewPost fails (rejected):

  • unwrap() will throw the rejected value

The thrown value/error will be caught in the catch block & your error message will be logged

If you were to log dispatch(addNewPost({ title, content, user: userId })).unwrap(), it would like this if there addNewPost succeeds:

enter image description here

Note: this is without the await keyword for your dispatch

Read more: https://redux-toolkit.js.org/rtk-query/usage/error-handling#error-display-examples

Desiccator answered 28/8, 2023 at 8:51 Comment(0)
C
0

From the reduxjs/toolkit docs

"However, it's common to want to write logic that looks at the success or failure of the actual request that was made. Redux Toolkit adds a .unwrap() function to the returned Promise, which will return a new Promise that either has the actual action.payload value from a fulfilled action, or throws an error if it's the rejected action"

Source

Charr answered 28/5, 2023 at 15:57 Comment(0)
D
0

The calling logic may wish to treat these actions as if they were the original promise contents. The promise returned by the dispatched thunk has an unwrap property which can be called to extract the payload of a fulfilled action or to throw either the error or, if available, payload created by rejectWithValue from a rejected action:

https://redux-toolkit.js.org/api/createAsyncThunk#unwrapping-result-actions

Delphina answered 29/4 at 6:37 Comment(0)
U
-1

If you need to access the error or success payload immediately after a mutation, you can chain .unwrap().

addPost({ id: 1, name: 'Example' })
.unwrap()
.then((payload) => console.log('fulfilled', payload))
.catch((error) => console.error('rejected', error))

As you can see, the .unwrap() method exposes the error and payload which you can use.

see ---> https://redux-toolkit.js.org/rtk-query/usage/error-handling

Unsure answered 21/11, 2023 at 3:57 Comment(1)
Your answer could be improved with additional supporting information. Please edit to add further details, such as citations or documentation, so that others can confirm that your answer is correct. You can find more information on how to write good answers in the help center.Hamm

© 2022 - 2024 — McMap. All rights reserved.