1.1.0 • Published 5 years ago

@xtream/yaem v1.1.0

Weekly downloads
22
License
-
Repository
github
Last release
5 years ago

yaem

yaem (Yet Another Entity Manager) is a pure @ngrx/entity porting that removes the Angular and @ngrx/store dependency so that it can be used also in React project.

The two most important feature are Memoized selectors and an entity adapter a simple utils that allows to manage entity in store preserving immutability.

Memoized selector (as reselect)

Memoized selectors allows to improve React performance, reducing application rerendering. If the input state is not changed the memoized selector just returns the precomputed value without recalculate it, preserving object reference and thus allowing memoized components and Pure component to not rerender.

Feature selector

The feature selector must me the root selector of each one. It selects the part of the state under the key specificied in the string as first argument. If for example the state has a root key named user:

import {createFeatureSelector} from '@xtream/yeam';
import {UserState} from '../reducers';

const selectUserState = createFeatureSelector<UserState>('user');

Simple selector

The createSelector api compose selector together memoizing each step and returning a function.

import {createFeatureSelector, createSelector} from '@xtream/yeam';
import {UserState} from '../reducers';

const selectUserState = createFeatureSelector<UserState>('user');

const selectName = createSelector(
  selectUserState,
  state => state.name
);

const selectSurname = createSelector(
    selectUserState,
    state => state.surname
);

const selectCompleteName = createSelector(
    selectName,
    selectSurname,
    (name, surname) => `${name} ${surname}`
);

Entity adapter

The entity adampter is an utility to easely manage entity in state keeping immutability. The exposed methos are

MethodUsage
removeAllClear all the entity in state
addOneAdd one entity
addManyAdd more entity
addAllOverwrite all the entity with the provided ones
updateOneUpdate an entity (do nothing if not exist)
updateManyUpdate all the provided entity (do nothing if not exist)
upsertOneUpdate if exits or add if not exists
upsertManyUpdate the ones that exists ad add the others
removeOneRemove entity
removeManyRemove all the provided entity
mapTransform all the entity using the provided function

All these methods require the state as a parameter. Each entity is assumed to have an id property but you can provide a selectId function to use a custom id using constructor.

For performance reason the entity state is organized like this:

{
  ids: any[],
  entities : {
    [id:any]: Entity
  }
}

Single update, add, or retrieve are realy fast thanks to the entities map object while ids array is used to keey track of all the present entity (or to keep them in a specific order).

To let the application access the state the entity adapter exposes 4 selectors:

SelectorUsage
selectIdsGet the list of all ids
selectEntitiesGet the dictionary of all the entity
selectAllGet the complete list of entities
selectTotalGet the number o entity in the state

Complete example

import {createEntityAdapter, EntityState} from '@xtream/yaem';
import {User} from '../models';
import * as usersActions from '../actions'

interface UsersState extends EntityState<User> {
  selectedUserId: string | null;
}

const adapter = createEntityAdapter<User>({
  selectId: user => user.username,
  sortComparer: (userA, userB) => userA.subscriptionDate.localeCompare(userB.subscriptionDate)
});

const defaultState = adapter.getInitialState({selectedUserId: null});

export default function reducer(state: UsersState = defaultState, action: usersActions.UsersActionTypes): UsersState {

  switch (action.type) {
    case usersActions.ADD_USER_SUCCESS:
      return adapter.addOne(action.user, state);
    case usersActions.DELETE_USER_SUCCESS:
      return adapter.removeOne(action.username, state);
    case usersActions.UPDATE_USER_SUCCESS:
      return adapter.upsertOne(action.user, state);
    default:
      return state;
  }
}

const {    
  selectIds,
  selectEntities,
  selectAll,
  selectTotal
} = adapter.getSelectors();

export {
  selectIds,
  selectEntities,
  selectAll,
  selectTotal
};
1.1.0

5 years ago

1.0.1

5 years ago

1.0.0

5 years ago

0.0.2

5 years ago

0.0.1

5 years ago