Избегайте дублирования вложенных объектов в хранилище избыточности

Я пробую redux-orm, и из того, что я могу собрать, redux-orm создает объект в магазине, ключом которого является значение, указанное через Model.name, для каждой зарегистрированной модели.

Что ж, чтобы создать свой редуктор сущностей, я использую combineReducers, передавая редукторы для всех своих сущностей, например так:

import { combineReducers } from 'redux';
import City from './cityReducer';
import Poi from './pointOfInterestReducer';

const entitiesReducer = combineReducers({
  City,
  Poi
});

export default entitiesReducer;

введите здесь описание изображения

И, наконец, вот как я создаю свой rootReducer, также используя combineReducers:

введите здесь описание изображения

Проблема в том, что я думаю, используя combineReducers, я дублирую ключи в своем магазине, как показано здесь:

введите здесь описание изображения

Есть ли у вас какие-либо идеи, как я могу избежать этого и сделать все мои модели прямыми потомками сущностей?

Что-то вроде entities>City, а не entities>City>City

Изменить: cityReducer.js

import orm from './../../orm/orm';
import * as types from '../../actions/actionTypes';

const loadCities = (state, action) => {
  // Create a Redux-ORM session from our entities "tables"
  const session = orm.session(state);
  // Get a reference to the correct version of model classes for this Session
  const { City } = session;
  const { cities } = action.payload;

  // Clear out any existing models from state so that we can avoid
  // conflicts from the new data coming in if data is reloaded

  City.all().toModelArray().forEach(city => city.delete());


  // Immutably update the session state as we insert items
  cities.forEach(city => City.parse(city));  
  return session.state;
};

const updateCity = (state, payload) => {
  const { id, newItemAttributes } = payload;

  const session = orm.session(state);
  const { City } = session;

  if (City.hasId(id)) {
    const modelInstance = City.withId(id);

    modelInstance.update(newItemAttributes);
  }

  return session.state;
};


const deleteCity = (state, payload) => {
  const { id } = payload;

  const session = orm.session(state);
  const { City } = session;

  if (City.hasId(id)) {
    const modelInstance = City.withId(id);

    // The session will immutably update its state reference
    modelInstance.delete();
  }

  return session.state;
};

const createCity = (state, payload) => {
  const { city } = payload;

  const session = orm.session(state);
  const { City } = session;

  City.parse(city);

  return session.state;
};

const citiesReducer = (dbState, action) => {
  const session = orm.session(dbState);
  switch (action.type) {
    case types.LOAD_CITIES_SUCCESS: return loadCities(dbState, action);
    case types.CREATE_CITY_SUCCESS: return createCity(dbState, action);
    case types.UPDATE_CITY_SUCCESS: return updateCity(dbState, action);
    case types.DELETE_CITY_SUCCESS: return deleteCity(dbState, action);
    default: return session.state;
  }
};

export default citiesReducer;

person eddy    schedule 01.09.2017    source источник
comment
плз поделитесь Городским Редьюсером   -  person emil    schedule 01.09.2017
comment
Сделанный! Пожалуйста, смотрите редактирование.   -  person eddy    schedule 01.09.2017


Ответы (1)


Существует два способа использования Redux-ORM для определения его структуры «таблиц» и написания логики редуктора для использования этих таблиц. Я привел примеры обоих подходов в своих сообщениях в блоге Practical Redux, Часть 1: Основы Redux-ORM, Practical Redux, часть 2: концепции и методы Redux-ORM и Практический пример Redux, часть 5: загрузка и отображение данных. (Обратите внимание, что эти сообщения охватывают использование Redux-ORM 0.8, а версия 0.9 имеет некоторые изменения API. Я перечислил эти изменения в Practical Redux, часть 9.)

Первый подход заключается в написании вашей логики редуктора, прикрепленной к классам вашей модели, и использовании экземпляра Redux-ORM ORM для создания редуктора, который создает «таблицы» и управляет ими для вас. Согласно примеру на обложке репозитория Redux-ORM:

import {createReducer} from "redux-orm";
import {orm} from "./models";

const rootReducer = combineReducers({
    entities: createReducer(orm)
});

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

import {orm} from "./models";

const initialState = orm.getEmptyState();

export default function entitiesReducer(state = initialState, action) {
    // handle other actions here if desired
    return state;
}

Другими словами, не определяйте отдельные "таблицы" для каждой модели самостоятельно. Позвольте Redux-ORM определить их либо автоматически в своем собственном редюсере, либо используя его для создания начального состояния для вашего редуктора сущностей.

person markerikson    schedule 01.09.2017