UNPKG

strapi-plugin-content-manager

Version:

A powerful UI to easily manage your data.

219 lines (193 loc) 6.87 kB
import { fromJS } from 'immutable'; import { getMaxTempKey } from '../../utils'; const initialState = fromJS({ componentsDataStructure: {}, contentTypeDataStructure: {}, formErrors: {}, initialData: {}, modifiedData: {}, shouldCheckErrors: false, modifiedDZName: null, }); const reducer = (state, action) => { switch (action.type) { case 'ADD_NON_REPEATABLE_COMPONENT_TO_FIELD': return state.updateIn(['modifiedData', ...action.keys], () => { const defaultDataStructure = state.getIn(['componentsDataStructure', action.componentUid]); return fromJS(defaultDataStructure); }); case 'ADD_REPEATABLE_COMPONENT_TO_FIELD': { return state .updateIn(['modifiedData', ...action.keys], list => { const defaultDataStructure = state .getIn(['componentsDataStructure', action.componentUid]) .set('__temp_key__', getMaxTempKey(list ? list.toJS() : []) + 1); if (list) { return list.push(defaultDataStructure); } return fromJS([defaultDataStructure]); }) .update('shouldCheckErrors', v => { if (action.shouldCheckErrors === true) { return !v; } return v; }); } case 'ADD_COMPONENT_TO_DYNAMIC_ZONE': return state .updateIn(['modifiedData', ...action.keys], list => { const defaultDataStructure = state .getIn(['componentsDataStructure', action.componentUid]) .set('__component', action.componentUid); if (list) { return list.push(defaultDataStructure); } return fromJS([defaultDataStructure]); }) .update('modifiedDZName', () => action.keys[0]) .update('shouldCheckErrors', v => { if (action.shouldCheckErrors === true) { return !v; } return v; }); case 'ADD_RELATION': return state.updateIn(['modifiedData', ...action.keys], list => { if (!Array.isArray(action.value) || !action.value.length) { return list; } const el = action.value[0].value; if (list) { return list.push(fromJS(el)); } return fromJS([el]); }); case 'INIT_FORM': { return state .update('formErrors', () => fromJS({})) .update('initialData', () => fromJS(action.initialValues)) .update('modifiedData', () => fromJS(action.initialValues)) .update('modifiedDZName', () => null) .update('shouldCheckErrors', () => false); } case 'MOVE_COMPONENT_FIELD': return state.updateIn(['modifiedData', ...action.pathToComponent], list => { return list .delete(action.dragIndex) .insert( action.hoverIndex, state.getIn(['modifiedData', ...action.pathToComponent, action.dragIndex]) ); }); case 'MOVE_COMPONENT_UP': return state .update('shouldCheckErrors', v => { if (action.shouldCheckErrors) { return !v; } return v; }) .updateIn(['modifiedData', action.dynamicZoneName], list => { return list .delete(action.currentIndex) .insert( action.currentIndex - 1, state.getIn(['modifiedData', action.dynamicZoneName, action.currentIndex]) ); }); case 'MOVE_COMPONENT_DOWN': return state .update('shouldCheckErrors', v => { if (action.shouldCheckErrors) { return !v; } return v; }) .updateIn(['modifiedData', action.dynamicZoneName], list => { return list .delete(action.currentIndex) .insert( action.currentIndex + 1, state.getIn(['modifiedData', action.dynamicZoneName, action.currentIndex]) ); }); case 'MOVE_FIELD': return state.updateIn(['modifiedData', ...action.keys], list => { return list.delete(action.dragIndex).insert(action.overIndex, list.get(action.dragIndex)); }); case 'ON_CHANGE': { let newState = state; const [nonRepeatableComponentKey] = action.keys; // This is used to set the initialData for inputs // that needs an asynchronous initial value like the UID field // This is just a temporary patch. // TODO : Refactor the default form creation (workflow) to accept async default values. if (action.shouldSetInitialValue) { newState = state.updateIn(['initialData', ...action.keys], () => { return action.value; }); } if ( action.keys.length === 2 && state.getIn(['modifiedData', nonRepeatableComponentKey]) === null ) { newState = newState.updateIn(['modifiedData', nonRepeatableComponentKey], () => fromJS({})); } return newState.updateIn(['modifiedData', ...action.keys], () => { return action.value; }); } case 'REMOVE_COMPONENT_FROM_DYNAMIC_ZONE': return state .update('shouldCheckErrors', v => { if (action.shouldCheckErrors) { return !v; } return v; }) .deleteIn(['modifiedData', action.dynamicZoneName, action.index]); case 'REMOVE_COMPONENT_FROM_FIELD': { const componentPathToRemove = ['modifiedData', ...action.keys]; return state.updateIn(componentPathToRemove, () => null); } case 'REMOVE_PASSWORD_FIELD': { return state.removeIn(['modifiedData', ...action.keys]); } case 'REMOVE_REPEATABLE_FIELD': { const componentPathToRemove = ['modifiedData', ...action.keys]; return state .update('shouldCheckErrors', v => { const hasErrors = state.get('formErrors').keySeq().size > 0; if (hasErrors) { return !v; } return v; }) .deleteIn(componentPathToRemove); } case 'REMOVE_RELATION': return state.removeIn(['modifiedData', ...action.keys.split('.')]); case 'SET_DEFAULT_DATA_STRUCTURES': return state .update('componentsDataStructure', () => fromJS(action.componentsDataStructure)) .update('contentTypeDataStructure', () => fromJS(action.contentTypeDataStructure)); case 'SET_FORM_ERRORS': { return state .update('modifiedDZName', () => null) .update('formErrors', () => fromJS(action.errors)); } case 'TRIGGER_FORM_VALIDATION': return state.update('shouldCheckErrors', v => { const hasErrors = state.get('formErrors').keySeq().size > 0; if (hasErrors) { return !v; } return v; }); default: return state; } }; export default reducer; export { initialState };