3

selectors takes 2 arguments, state and props, but how can we handle selectors for relational data ?

initialState = {
  department  :{ids:[1],byId:{name:'dep 1',id:1,parent:null}}
  sections    :{ids:[2],byId:{name:'section 1.1',id:2,parent:1}}
  subsections :{ids:[3],byId:{name:'subsection 1.1.1',id:3,parent:2}}
}

here department is aparent of n(sections) and grandparent of n(subsections)

in <Department id="1" /> i want to select department 1 and all its children.

how can i write such selector without passing the id of the department i need to the selector ?

Zalaboza
  • 8,899
  • 16
  • 77
  • 142

2 Answers2

0

You might use a router (react-router) to pass such keys by url segments, then you get access to the ids you need, ie:

mapStateToProps(state, ownProps) {
  // then get access to id here
  console.log(ownProps.params.department_id);
}
Elise Chant
  • 5,048
  • 3
  • 29
  • 36
0

Here you'll find an implementation that - i hope - will answer to your first question : "how can we handle selectors for relational data ?"

import { createSelector } from "reselect";

const state = {
  departments: [{ id: 1, byId: { name: "dep 1", id: 1, parent: null } }],
  sections: [{ id: 2, byId: { name: "section 1.1", id: 2, parent: 1 } }],
  subsections: [
    {
      id: 3,
      byId: { name: "subsection 1.1.1", id: 3, parent: 2 }
    }
  ]
};

const clone = obj => JSON.parse(JSON.stringify(obj));

const bottomUp = (...levels) => 
  levels.reduce((children, parents) => {
    const p = clone(parents);
    const addToParent = child => {
      const parent = p.find(par => par.id === child.byId.parent);
      if (parent) {
        if (parent.children) {
          parent.children.push(child);
        } else {
          parent.children = [child];
        }
      }
    }
    children.forEach(addToParent);
    return p;
  });

const selectSubs = state => state.subsections;
const selectSecs = state => state.sections;
const selectDeps = state => state.departments;

const selectHierarchy = createSelector(
  selectSubs,
  selectSecs,
  selectDeps,
  bottomUp
);

console.log(selectHierarchy(state));


This new selector will return :

enter image description here

As you can see, since I didn't fully understand your store structure, i performed few changes in it : each domain became an array and each id became a number.

I hope it will help ... Cheers

LIIT
  • 496
  • 6
  • 16