Reputation: 123
Destructing object form object doesn't create new object so React won't rerender if you replace property of object we were destructing from with newly created through destruction object
inside of some thunk:
const {
stock: { bag },
} = getState();
changing property of 'bag' and assigning this object in reducer to the place where he was destructed (stock property) won't make react rerender, but creating new property or creating new object explicitly and assigning this object to the place where he was destructed will force react to rerender
Upvotes: 0
Views: 249
Reputation: 8376
Just to dig deeper into what might be happening, the outcome of changing a variable was assigned via destructuring depends on the type of that variable. If it is of referential type (which in JS is, for the most part, Object), any mutation (reassignment) of its properties will result in a change in the original object:
> const o = { x: { y: { z: 2 } } }
> let { y } = o.x // <- y is a reference to o.x.y and is an object
> y.z = 5
> o
{ x: { y: { z: 5 } } }
but if we continue and try to change z
,
> let { z } = o.x.y; // <- z is a number
> z = 20
> o
{ x: { y: { z: 5 } } }
same works for assignment that goes deep into the source object, i.e., lots of brackets on the left-hand side:
> let { x: { y: { z } } } = o
> z = 100
> o
{ x: { y: { z: 5 } } }
Given this, it might be that bag
in your case is a value of referential type (you also mentioned changing a property of it). React performs a referential equality check, the old reference to an object is equal the new one, which means the state didn't change, which explains why a component doesn't get re-rendered.
Upvotes: 1
Reputation: 6529
You are correct, destructuring an object will not trigger a rerender.
If this code is inside a thunk, you’ll need to dispatch an action in order to trigger a rerender.
If this code were in a component, you would need to call setState
(Or dispatch an action) to trigger a rerender.
Upvotes: 1