Как изменить / заменить React Redux State на двойной вложенный массив объектов? - PullRequest
1 голос
/ 11 июня 2019

Мое избыточное состояние имеет SessionList, который является массивом SessionObjects, а каждый SessionObject имеет массив HandObjects.

Я использую состояние для обновления отдельных объектов SessionObject, добавляя новые объекты HandObject, однако я хочу обновить хранилище с избыточностью с помощью моего обновленного объекта SessionObject (по возможности, неизменного).

индекс SessionObject в пределах SessionList равен action.payload.Id (я думаю? Я покажу мой конструктор SessionObject)

** Добавление сеансов работает просто отлично, и я обновляю сеанс только с сеансом, уже находящимся в магазине

Я перепробовал каждую ссылку, которую смог найти, но мой код достаточно отличается, и я не могу корректно обновить свой SessionList.

мой редуктор, с начальным состоянием store.js (где мои редукторы)

const initialState = {
    SessionList: [],
}
...
case "UPDATE_SESSION":
            //action.payload is a SessionObject
            //action.payload.Id is the Id that i want to update
            // i want to set SessionList[action.payload.Id] = action.payload
            state = {
                ...state,
                SessionList : state.SessionList.map((item, index) => {
                    if (index != action.payload.id) {
                      return item
                    }

                    return action.payload
                    //This code doesn't visibly do anything that I can find
                  })

                // *******FIRST TRY*******
                // ...state,
                //  SessionList: {
                //     ...state.SessionList,
                //     SessionList[action.payload.id] : action.payload 
//syntax error, but basically what i want to do
                //      }
                // }
                // ***********************
            };
            break;

Конструктор SessionObject Session.js

export function SessionObject(_id, _name, _hands) {
    this.id = _id, //int
    this.name = _name, //string
    this.HandList = _hands //array of HandObject objects
}
var defaultSession = new SessionObject(0, "default", []);

* в случае, если я делаю это неправильно, Я звоню (Session.js)

this.props.navigation.state.params.updateMethod(this.state.Session); //update store

из дочернего компонента стека-навигатора.
затем в родительском компоненте, Я звоню (Home.js)

UpdateSession = (session) => {
      this.props.updateSession(session);
    };

Мой диспетчер выглядит так: (Home.js)

updateSession: (session) => {
        dispatch({
          type: "UPDATE_SESSION",
          payload: session
        });
      }

После тестирования я уверен, что мой редуктор вызывается правильно.

Я хочу заменить SessionObject на action.payload в правильном индексе SessionList.

РЕДАКТИРОВАТЬ *

Session.js

addItem = () => {
        this.setState((state, props) => ({
        Session : {
          ...state,
          HandList: [...state.Session.HandList, new HandObject(state.HandCount)]
        },
        HandCount : state.HandCount + 1,
        }));
        this.props.navigation.state.params.updateMethod(this.state.Session); //update store
    };

Состояние в Session.js является SessionObject

1 Ответ

3 голосов
/ 11 июня 2019

Чтобы получить результат SessionList[action.payload.Id], вам нужно инициализировать SessionList как объект, а не как массив. Тогда вы можете обновить соответственно.

   const initialState = {
      SessionList: {},
   }

   case "UPDATE_SESSION":
            state = {
                ...state,
                SessionList: Object.keys(state.SessionList).reduce((acc, id) => {
                    if (id === action.payload.Id) {
                      acc[id] = action.payload;
                    } else {
                      acc[id] = state.SessionList[id];
                    }

                    return acc;
                  }, {});
            };

Обновление

По запросу здесь , следующие добавить , обновить , заменить и удалить обработчики без изменения SessionList к объекту.

const initialState = {
     SessionList: [],
}

Примечание: action.payload (где бы он ни использовался) является объектом сеанса.

Добавить

state = {
    ...state,
    SessionList: [...state.SessionList, action.payload];
};

Обновление

state = {
    ...state,
    SessionList: state.SessionList.map((session) => {
        if (session.Id === action.payload.Id) {
           return Object.assign({}, session, action.payload);
        }

        return session;
    })
};

Заменить

state = {
    ...state,
    SessionList: state.SessionList.map((session) => {
        if (session.Id === action.payload.Id) {
           return action.payload;
        }

        return session;
    })
};

Удалить

state = {
    ...state,
    SessionList: state.SessionList.filter((session) => session.Id !== action.payload.Id)
};
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...