P
P
Pogran2016-09-22 10:35:58
React
Pogran, 2016-09-22 10:35:58

What is the best way to change the state into a reducer if the structure is a composite object?

I have this structure

const initialState = {
  _id: '',
  structure: {
    0: {
      id: 0,
      _key: false,
      _value: 1,
      type: 'object',
      childIds: []
    }
  },
  name: '',
  createdAt: '',
  updatedAt: ''
};

And I do an action to change one element in the structure
, I do it like this
const updateChildLevelNode = structure => {
        const { id, value, key } = action;

        structure[id]._value = value;
        structure[id]._key = key;

        return structure;
      };

      return {
        ...state,
        structure: updateChildLevelNode(state.structure)
      };

Maybe there is a more practical way not to create the updateChildLevelNode function, but to do everything right away in return?

Answer the question

In order to leave comments, you need to log in

1 answer(s)
N
Nikita Gushchin, 2016-09-22
@Pogran

First: you are updating the structure incorrectly - in no case should you mutate an object.
Secondly: why not immediately form an action object with the necessary property names? (_key, _value)

const action = {
  id: 132,
  _key: 'some key',
  _value: 564
}

return {
  ...state,
  structure: {
    ...state.structure,
    [id]: { ...(state.structure[id] || {}), ...action },
  }
}

The expression below is needed so as not to get an error if suddenly state.structure[id] === udefined. If you are sure that this will never happen - you can leave only ...state.structure[id].
If you are using lodash (or similar) in your project, you can delete it like this:
import _ from 'lodash'

const { id, parentId } = action
// удаляем из структуры свойство с именем id
const nextStructure = _.omit(state.structure, id)
return {
  ...state,
  structure: {
    ...nextStructure,
    [parentId]: {
      ...nextStructure[parentId],
      childIds: nextStructure[parentId].childIds.filter(cId => cId !== id)
    }
  }
}

If you are not using lodash, then you can do this (link to documentation ):
const { id, parentId } = action
// в данном случае у нас будет переменная
// const removed = state.structure[id]
// а в переменную nextStructure попадут все значения, кроме id
const { [id]: removed, ...nextStructure } = state.structure
return {
  ...state,
  structure: {
    ...nextStructure,
    [parentId]: {
      ...nextStructure[parentId],
      childIds: nextStructure[parentId].childIds.filter(cId => cId !== id)
    }
  }
}

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question