mirror of
https://github.com/strapi/strapi.git
synced 2025-12-27 07:03:38 +00:00
Add redux to CTB
Signed-off-by: HichamELBSI <elabbassih@gmail.com>
This commit is contained in:
parent
e8e93be070
commit
58a7665c63
@ -19,8 +19,8 @@
|
||||
"type": "string"
|
||||
},
|
||||
"categories": {
|
||||
"via": "addresses",
|
||||
"collection": "category",
|
||||
"via": "addresses",
|
||||
"dominant": true
|
||||
},
|
||||
"cover": {
|
||||
|
||||
@ -16,8 +16,8 @@
|
||||
"type": "string"
|
||||
},
|
||||
"addresses": {
|
||||
"collection": "address",
|
||||
"via": "categories"
|
||||
"via": "categories",
|
||||
"collection": "address"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -1,8 +1,9 @@
|
||||
{
|
||||
"collectionName": "components_blog_test_comos",
|
||||
"info": {
|
||||
"name": "test como",
|
||||
"icon": "ad"
|
||||
"name": "test comp",
|
||||
"icon": "ad",
|
||||
"description": ""
|
||||
},
|
||||
"options": {},
|
||||
"attributes": {
|
||||
|
||||
@ -97,6 +97,7 @@ Object.keys(plugins).forEach(current => {
|
||||
}, {});
|
||||
|
||||
// Inject plugins reducers
|
||||
console.log(plugin.reducers);
|
||||
const pluginReducers = plugin.reducers || {};
|
||||
|
||||
Object.keys(pluginReducers).forEach(reducerName => {
|
||||
|
||||
@ -10,6 +10,7 @@ import checkStore from './checkStore';
|
||||
|
||||
export function injectReducerFactory(store, isValid) {
|
||||
return function injectReducer(key, reducer) {
|
||||
// console.log(key, reducer);
|
||||
if (!isValid) checkStore(store);
|
||||
|
||||
invariant(
|
||||
|
||||
@ -109,18 +109,18 @@ const formatLayoutWithMetas = (contentTypeConfiguration, ctUid, models) => {
|
||||
metadatas: get(contentTypeConfiguration, ['metadatas', attribute.name, 'edit'], {}),
|
||||
};
|
||||
|
||||
if (fieldSchema.type === 'relation') {
|
||||
const queryInfos = ctUid
|
||||
? generateRelationQueryInfosForComponents(
|
||||
contentTypeConfiguration,
|
||||
attribute.name,
|
||||
ctUid,
|
||||
models
|
||||
)
|
||||
: generateRelationQueryInfos(contentTypeConfiguration, attribute.name, models);
|
||||
// if (fieldSchema.type === 'relation') {
|
||||
// const queryInfos = ctUid
|
||||
// ? generateRelationQueryInfosForComponents(
|
||||
// contentTypeConfiguration,
|
||||
// attribute.name,
|
||||
// ctUid,
|
||||
// models
|
||||
// )
|
||||
// : generateRelationQueryInfos(contentTypeConfiguration, attribute.name, models);
|
||||
|
||||
set(data, 'queryInfos', queryInfos);
|
||||
}
|
||||
// set(data, 'queryInfos', queryInfos);
|
||||
// }
|
||||
|
||||
return data;
|
||||
});
|
||||
|
||||
@ -0,0 +1,11 @@
|
||||
export const ADD_COMPONENTS_TO_DYNAMIC_ZONE = 'ContentTypeBuilder/FormModal/ADD_COMPONENTS_TO_DYNAMIC_ZONE';
|
||||
export const ON_CHANGE = 'ContentTypeBuilder/FormModal/ON_CHANGE';
|
||||
export const ON_CHANGE_ALLOWED_TYPE = 'ContentTypeBuilder/FormModal/ON_CHANGE_ALLOWED_TYPE';
|
||||
export const RESET_PROPS = 'ContentTypeBuilder/FormModal/RESET_PROPS';
|
||||
export const RESET_PROPS_AND_SET_FORM_FOR_ADDING_AN_EXISTING_COMPO = 'ContentTypeBuilder/FormModal/RESET_PROPS_AND_SET_FORM_FOR_ADDING_AN_EXISTING_COMPO';
|
||||
export const RESET_PROPS_AND_SAVE_CURRENT_DATA = 'ContentTypeBuilder/FormModal/RESET_PROPS_AND_SAVE_CURRENT_DATA';
|
||||
export const RESET_PROPS_AND_SET_THE_FORM_FOR_ADDING_A_COMPO_TO_A_DZ = 'ContentTypeBuilder/FormModal/RESET_PROPS_AND_SET_THE_FORM_FOR_ADDING_A_COMPO_TO_A_DZ';
|
||||
export const SET_DATA_TO_EDIT = 'ContentTypeBuilder/FormModal/SET_DATA_TO_EDIT';
|
||||
export const SET_ATTRIBUTE_DATA_SCHEMA = 'ContentTypeBuilder/FormModal/SET_ATTRIBUTE_DATA_SCHEMA';
|
||||
export const SET_DYNAMIC_ZONE_DATA_SCHEMA = 'ContentTypeBuilder/FormModal/SET_DYNAMIC_ZONE_DATA_SCHEMA';
|
||||
export const SET_ERRORS = 'ContentTypeBuilder/FormModal/SET_ERRORS';
|
||||
@ -1,4 +1,4 @@
|
||||
import React, { useCallback, useEffect, useReducer, useRef, useState } from 'react';
|
||||
import React, { useCallback, useEffect, useRef, useState, useMemo } from 'react';
|
||||
import {
|
||||
HeaderModal,
|
||||
HeaderModalTitle,
|
||||
@ -17,6 +17,7 @@ import { Inputs } from '@buffetjs/custom';
|
||||
import { useHistory, useLocation } from 'react-router-dom';
|
||||
import { FormattedMessage } from 'react-intl';
|
||||
import { get, has, isEmpty, set, toLower, toString, upperFirst } from 'lodash';
|
||||
import { useSelector, useDispatch } from 'react-redux';
|
||||
import pluginId from '../../pluginId';
|
||||
import useDataManager from '../../hooks/useDataManager';
|
||||
import AttributeOption from '../../components/AttributeOption';
|
||||
@ -41,9 +42,21 @@ import {
|
||||
import forms from './forms';
|
||||
import { createComponentUid, createUid } from './utils/createUid';
|
||||
import { NAVLINKS, INITIAL_STATE_DATA } from './utils/staticData';
|
||||
import init from './init';
|
||||
import reducer, { initialState } from './reducer';
|
||||
import CustomButton from './CustomButton';
|
||||
import makeSelectFormModal from './selectors';
|
||||
import {
|
||||
SET_DATA_TO_EDIT,
|
||||
SET_DYNAMIC_ZONE_DATA_SCHEMA,
|
||||
SET_ATTRIBUTE_DATA_SCHEMA,
|
||||
ADD_COMPONENTS_TO_DYNAMIC_ZONE,
|
||||
ON_CHANGE_ALLOWED_TYPE,
|
||||
SET_ERRORS,
|
||||
ON_CHANGE,
|
||||
RESET_PROPS_AND_SET_THE_FORM_FOR_ADDING_A_COMPO_TO_A_DZ,
|
||||
RESET_PROPS_AND_SET_FORM_FOR_ADDING_AN_EXISTING_COMPO,
|
||||
RESET_PROPS_AND_SAVE_CURRENT_DATA,
|
||||
RESET_PROPS,
|
||||
} from './constants';
|
||||
|
||||
/* eslint-disable indent */
|
||||
/* eslint-disable react/no-array-index-key */
|
||||
@ -51,7 +64,9 @@ import CustomButton from './CustomButton';
|
||||
const FormModal = () => {
|
||||
const [state, setState] = useState(INITIAL_STATE_DATA);
|
||||
const [showConfirmModal, setShowConfirmModal] = useState(false);
|
||||
const [reducerState, dispatch] = useReducer(reducer, initialState, init);
|
||||
const formModalSelector = useMemo(makeSelectFormModal, []);
|
||||
const dispatch = useDispatch();
|
||||
const reducerState = useSelector(state => formModalSelector(state), []);
|
||||
const { push } = useHistory();
|
||||
const { search } = useLocation();
|
||||
const { emitEvent, formatMessage } = useGlobalContext();
|
||||
@ -83,7 +98,7 @@ const FormModal = () => {
|
||||
initialData,
|
||||
isCreatingComponentWhileAddingAField,
|
||||
modifiedData,
|
||||
} = reducerState.toJS();
|
||||
} = reducerState;
|
||||
|
||||
useEffect(() => {
|
||||
if (!isEmpty(search)) {
|
||||
@ -206,7 +221,7 @@ const FormModal = () => {
|
||||
// Edit category
|
||||
if (modalType === 'editCategory' && actionType === 'edit') {
|
||||
dispatch({
|
||||
type: 'SET_DATA_TO_EDIT',
|
||||
type: SET_DATA_TO_EDIT,
|
||||
data: {
|
||||
name: query.get('categoryName'),
|
||||
},
|
||||
@ -220,7 +235,7 @@ const FormModal = () => {
|
||||
actionType === 'create'
|
||||
) {
|
||||
dispatch({
|
||||
type: 'SET_DATA_TO_EDIT',
|
||||
type: SET_DATA_TO_EDIT,
|
||||
data: {
|
||||
draftAndPublish: true,
|
||||
},
|
||||
@ -243,7 +258,7 @@ const FormModal = () => {
|
||||
);
|
||||
|
||||
dispatch({
|
||||
type: 'SET_DATA_TO_EDIT',
|
||||
type: SET_DATA_TO_EDIT,
|
||||
data: {
|
||||
name,
|
||||
collectionName,
|
||||
@ -258,7 +273,7 @@ const FormModal = () => {
|
||||
const data = get(allDataSchema, pathToSchema, {});
|
||||
|
||||
dispatch({
|
||||
type: 'SET_DATA_TO_EDIT',
|
||||
type: SET_DATA_TO_EDIT,
|
||||
data: {
|
||||
name: data.schema.name,
|
||||
category: data.category,
|
||||
@ -290,7 +305,7 @@ const FormModal = () => {
|
||||
};
|
||||
|
||||
dispatch({
|
||||
type: 'SET_DYNAMIC_ZONE_DATA_SCHEMA',
|
||||
type: SET_DYNAMIC_ZONE_DATA_SCHEMA,
|
||||
attributeToEdit,
|
||||
});
|
||||
}
|
||||
@ -325,7 +340,7 @@ const FormModal = () => {
|
||||
}
|
||||
|
||||
dispatch({
|
||||
type: 'SET_ATTRIBUTE_DATA_SCHEMA',
|
||||
type: SET_ATTRIBUTE_DATA_SCHEMA,
|
||||
attributeType,
|
||||
nameToSetForRelation: get(collectionTypesForRelation, ['0', 'title'], 'error'),
|
||||
targetUid: get(collectionTypesForRelation, ['0', 'uid'], 'error'),
|
||||
@ -520,7 +535,7 @@ const FormModal = () => {
|
||||
target: { name, components, shouldAddComponents },
|
||||
}) => {
|
||||
dispatch({
|
||||
type: 'ADD_COMPONENTS_TO_DYNAMIC_ZONE',
|
||||
type: ADD_COMPONENTS_TO_DYNAMIC_ZONE,
|
||||
name,
|
||||
components,
|
||||
shouldAddComponents,
|
||||
@ -529,7 +544,7 @@ const FormModal = () => {
|
||||
|
||||
const handleChangeMediaAllowedTypes = ({ target: { name, value } }) => {
|
||||
dispatch({
|
||||
type: 'ON_CHANGE_ALLOWED_TYPE',
|
||||
type: ON_CHANGE_ALLOWED_TYPE,
|
||||
name,
|
||||
value,
|
||||
});
|
||||
@ -604,29 +619,29 @@ const FormModal = () => {
|
||||
delete clonedErrors[name];
|
||||
|
||||
dispatch({
|
||||
type: 'SET_ERRORS',
|
||||
type: SET_ERRORS,
|
||||
errors: clonedErrors,
|
||||
});
|
||||
|
||||
dispatch({
|
||||
type: 'ON_CHANGE',
|
||||
type: ON_CHANGE,
|
||||
keys: name.split('.'),
|
||||
value: val,
|
||||
...rest,
|
||||
});
|
||||
},
|
||||
[formErrors, state.actionType, toggleConfirmModal]
|
||||
[dispatch, formErrors, state.actionType, toggleConfirmModal]
|
||||
);
|
||||
|
||||
const handleConfirmDisableDraftAndPublish = useCallback(() => {
|
||||
dispatch({
|
||||
type: 'ON_CHANGE',
|
||||
type: ON_CHANGE,
|
||||
keys: ['draftAndPublish'],
|
||||
value: false,
|
||||
});
|
||||
|
||||
toggleConfirmModal();
|
||||
}, [toggleConfirmModal]);
|
||||
}, [dispatch, toggleConfirmModal]);
|
||||
|
||||
const handleSubmit = async (e, shouldContinue = isCreating) => {
|
||||
e.preventDefault();
|
||||
@ -771,7 +786,7 @@ const FormModal = () => {
|
||||
if (isDynamicZoneAttribute) {
|
||||
// Step 1 of adding a component to a DZ, the user has the option to create a component
|
||||
dispatch({
|
||||
type: 'RESET_PROPS_AND_SET_THE_FORM_FOR_ADDING_A_COMPO_TO_A_DZ',
|
||||
type: RESET_PROPS_AND_SET_THE_FORM_FOR_ADDING_A_COMPO_TO_A_DZ,
|
||||
});
|
||||
|
||||
push({ search: isCreating ? nextSearch : '' });
|
||||
@ -810,7 +825,7 @@ const FormModal = () => {
|
||||
// The first step is either needed to create a component or just to navigate
|
||||
// To the modal for adding a "common field"
|
||||
dispatch({
|
||||
type: 'RESET_PROPS_AND_SET_FORM_FOR_ADDING_AN_EXISTING_COMPO',
|
||||
type: RESET_PROPS_AND_SET_FORM_FOR_ADDING_AN_EXISTING_COMPO,
|
||||
});
|
||||
|
||||
// We don't want all the props to be reset
|
||||
@ -878,7 +893,7 @@ const FormModal = () => {
|
||||
// Here we clear the reducer state but we also keep the created component
|
||||
// If we were to create the component before
|
||||
dispatch({
|
||||
type: 'RESET_PROPS_AND_SAVE_CURRENT_DATA',
|
||||
type: RESET_PROPS_AND_SAVE_CURRENT_DATA,
|
||||
});
|
||||
|
||||
// Terminate because we don't want the reducer to be entirely reset
|
||||
@ -909,7 +924,7 @@ const FormModal = () => {
|
||||
// Add the field to the schema
|
||||
addAttribute(modifiedData, state.forTarget, state.targetUid, false);
|
||||
|
||||
dispatch({ type: 'RESET_PROPS' });
|
||||
dispatch({ type: RESET_PROPS });
|
||||
|
||||
// Open modal attribute for adding attr to component
|
||||
|
||||
@ -996,13 +1011,13 @@ const FormModal = () => {
|
||||
}
|
||||
|
||||
dispatch({
|
||||
type: 'RESET_PROPS',
|
||||
type: RESET_PROPS,
|
||||
});
|
||||
} catch (err) {
|
||||
const errors = getYupInnerErrors(err);
|
||||
|
||||
dispatch({
|
||||
type: 'SET_ERRORS',
|
||||
type: SET_ERRORS,
|
||||
errors,
|
||||
});
|
||||
}
|
||||
@ -1014,7 +1029,7 @@ const FormModal = () => {
|
||||
const onClosed = () => {
|
||||
setState(INITIAL_STATE_DATA);
|
||||
dispatch({
|
||||
type: 'RESET_PROPS',
|
||||
type: RESET_PROPS,
|
||||
});
|
||||
};
|
||||
const onOpened = () => {
|
||||
|
||||
@ -1,5 +0,0 @@
|
||||
function init(initialState) {
|
||||
return initialState;
|
||||
}
|
||||
|
||||
export default init;
|
||||
@ -4,148 +4,169 @@ import { snakeCase } from 'lodash';
|
||||
import makeUnique from '../../utils/makeUnique';
|
||||
import { createComponentUid } from './utils/createUid';
|
||||
import { shouldPluralizeName, shouldPluralizeTargetAttribute } from './utils/relations';
|
||||
import {
|
||||
ADD_COMPONENTS_TO_DYNAMIC_ZONE,
|
||||
ON_CHANGE,
|
||||
ON_CHANGE_ALLOWED_TYPE,
|
||||
RESET_PROPS,
|
||||
RESET_PROPS_AND_SET_FORM_FOR_ADDING_AN_EXISTING_COMPO,
|
||||
RESET_PROPS_AND_SAVE_CURRENT_DATA,
|
||||
RESET_PROPS_AND_SET_THE_FORM_FOR_ADDING_A_COMPO_TO_A_DZ,
|
||||
SET_DATA_TO_EDIT,
|
||||
SET_ATTRIBUTE_DATA_SCHEMA,
|
||||
SET_DYNAMIC_ZONE_DATA_SCHEMA,
|
||||
SET_ERRORS,
|
||||
} from './constants';
|
||||
|
||||
const initialState = fromJS({
|
||||
const initialState = {
|
||||
formErrors: {},
|
||||
modifiedData: {},
|
||||
initialData: {},
|
||||
componentToCreate: {},
|
||||
isCreatingComponentWhileAddingAField: false,
|
||||
});
|
||||
};
|
||||
|
||||
const formModalReducer = (jsonState = initialState, action) => {
|
||||
const state = fromJS(jsonState);
|
||||
|
||||
const reducer = (state, action) => {
|
||||
switch (action.type) {
|
||||
case 'ADD_COMPONENTS_TO_DYNAMIC_ZONE': {
|
||||
case ADD_COMPONENTS_TO_DYNAMIC_ZONE: {
|
||||
const { name, components, shouldAddComponents } = action;
|
||||
|
||||
return state.updateIn(['modifiedData', name], list => {
|
||||
let updatedList = list;
|
||||
return state
|
||||
.updateIn(['modifiedData', name], list => {
|
||||
let updatedList = list;
|
||||
|
||||
if (shouldAddComponents) {
|
||||
updatedList = list.concat(components);
|
||||
} else {
|
||||
updatedList = list.filter(comp => {
|
||||
return components.indexOf(comp) === -1;
|
||||
});
|
||||
}
|
||||
|
||||
return List(makeUnique(updatedList.toJS()));
|
||||
});
|
||||
}
|
||||
case 'ON_CHANGE':
|
||||
return state.update('modifiedData', obj => {
|
||||
const {
|
||||
selectedContentTypeFriendlyName,
|
||||
keys,
|
||||
value,
|
||||
oneThatIsCreatingARelationWithAnother,
|
||||
} = action;
|
||||
const hasDefaultValue = Boolean(obj.getIn(['default']));
|
||||
|
||||
// There is no need to remove the default key if the default value isn't defined
|
||||
if (hasDefaultValue && keys.length === 1 && keys.includes('type')) {
|
||||
const previousType = obj.getIn(['type']);
|
||||
|
||||
if (previousType && ['date', 'datetime', 'time'].includes(previousType)) {
|
||||
return obj.updateIn(keys, () => value).remove('default');
|
||||
}
|
||||
}
|
||||
|
||||
if (keys.length === 1 && keys.includes('nature')) {
|
||||
return obj
|
||||
.update('nature', () => value)
|
||||
.update('dominant', () => {
|
||||
if (value === 'manyToMany') {
|
||||
return true;
|
||||
}
|
||||
|
||||
return null;
|
||||
})
|
||||
.update('name', oldValue => {
|
||||
return pluralize(snakeCase(oldValue), shouldPluralizeName(value));
|
||||
})
|
||||
.update('targetAttribute', oldValue => {
|
||||
if (['oneWay', 'manyWay'].includes(value)) {
|
||||
return '-';
|
||||
}
|
||||
|
||||
return pluralize(
|
||||
oldValue === '-' ? snakeCase(oneThatIsCreatingARelationWithAnother) : oldValue,
|
||||
shouldPluralizeTargetAttribute(value)
|
||||
);
|
||||
})
|
||||
.update('targetColumnName', oldValue => {
|
||||
if (['oneWay', 'manyWay'].includes(value)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return oldValue;
|
||||
if (shouldAddComponents) {
|
||||
updatedList = list.concat(components);
|
||||
} else {
|
||||
updatedList = list.filter(comp => {
|
||||
return components.indexOf(comp) === -1;
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
if (keys.length === 1 && keys.includes('target')) {
|
||||
const { targetContentTypeAllowedRelations } = action;
|
||||
let didChangeNatureBecauseOfRestrictedRelation = false;
|
||||
return List(makeUnique(updatedList.toJS()));
|
||||
})
|
||||
.toJS();
|
||||
}
|
||||
case ON_CHANGE:
|
||||
return state
|
||||
.update('modifiedData', obj => {
|
||||
const {
|
||||
selectedContentTypeFriendlyName,
|
||||
keys,
|
||||
value,
|
||||
oneThatIsCreatingARelationWithAnother,
|
||||
} = action;
|
||||
const hasDefaultValue = Boolean(obj.getIn(['default']));
|
||||
|
||||
// There is no need to remove the default key if the default value isn't defined
|
||||
if (hasDefaultValue && keys.length === 1 && keys.includes('type')) {
|
||||
const previousType = obj.getIn(['type']);
|
||||
|
||||
if (previousType && ['date', 'datetime', 'time'].includes(previousType)) {
|
||||
return obj.updateIn(keys, () => value).remove('default');
|
||||
}
|
||||
}
|
||||
|
||||
if (keys.length === 1 && keys.includes('nature')) {
|
||||
return obj
|
||||
.update('nature', () => value)
|
||||
.update('dominant', () => {
|
||||
if (value === 'manyToMany') {
|
||||
return true;
|
||||
}
|
||||
|
||||
return null;
|
||||
})
|
||||
.update('name', oldValue => {
|
||||
return pluralize(snakeCase(oldValue), shouldPluralizeName(value));
|
||||
})
|
||||
.update('targetAttribute', oldValue => {
|
||||
if (['oneWay', 'manyWay'].includes(value)) {
|
||||
return '-';
|
||||
}
|
||||
|
||||
return pluralize(
|
||||
oldValue === '-' ? snakeCase(oneThatIsCreatingARelationWithAnother) : oldValue,
|
||||
shouldPluralizeTargetAttribute(value)
|
||||
);
|
||||
})
|
||||
.update('targetColumnName', oldValue => {
|
||||
if (['oneWay', 'manyWay'].includes(value)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return oldValue;
|
||||
});
|
||||
}
|
||||
|
||||
if (keys.length === 1 && keys.includes('target')) {
|
||||
const { targetContentTypeAllowedRelations } = action;
|
||||
let didChangeNatureBecauseOfRestrictedRelation = false;
|
||||
|
||||
return obj
|
||||
.update('target', () => value)
|
||||
.update('nature', currentNature => {
|
||||
if (targetContentTypeAllowedRelations === null) {
|
||||
return currentNature;
|
||||
}
|
||||
|
||||
if (!targetContentTypeAllowedRelations.includes(currentNature)) {
|
||||
didChangeNatureBecauseOfRestrictedRelation = true;
|
||||
|
||||
return targetContentTypeAllowedRelations[0];
|
||||
}
|
||||
|
||||
return obj
|
||||
.update('target', () => value)
|
||||
.update('nature', currentNature => {
|
||||
if (targetContentTypeAllowedRelations === null) {
|
||||
return currentNature;
|
||||
}
|
||||
})
|
||||
.update('name', () => {
|
||||
if (didChangeNatureBecauseOfRestrictedRelation) {
|
||||
return pluralize(
|
||||
snakeCase(selectedContentTypeFriendlyName),
|
||||
shouldPluralizeName(targetContentTypeAllowedRelations[0])
|
||||
);
|
||||
}
|
||||
|
||||
if (!targetContentTypeAllowedRelations.includes(currentNature)) {
|
||||
didChangeNatureBecauseOfRestrictedRelation = true;
|
||||
|
||||
return targetContentTypeAllowedRelations[0];
|
||||
}
|
||||
|
||||
return currentNature;
|
||||
})
|
||||
.update('name', () => {
|
||||
if (didChangeNatureBecauseOfRestrictedRelation) {
|
||||
return pluralize(
|
||||
snakeCase(selectedContentTypeFriendlyName),
|
||||
shouldPluralizeName(targetContentTypeAllowedRelations[0])
|
||||
|
||||
shouldPluralizeName(obj.get('nature'))
|
||||
);
|
||||
}
|
||||
})
|
||||
.update('targetAttribute', () => {
|
||||
if (['oneWay', 'manyWay'].includes(obj.get('nature'))) {
|
||||
return '-';
|
||||
}
|
||||
|
||||
return pluralize(
|
||||
snakeCase(selectedContentTypeFriendlyName),
|
||||
if (
|
||||
didChangeNatureBecauseOfRestrictedRelation &&
|
||||
['oneWay', 'manyWay'].includes(targetContentTypeAllowedRelations[0])
|
||||
) {
|
||||
return '-';
|
||||
}
|
||||
|
||||
shouldPluralizeName(obj.get('nature'))
|
||||
);
|
||||
})
|
||||
.update('targetAttribute', () => {
|
||||
if (['oneWay', 'manyWay'].includes(obj.get('nature'))) {
|
||||
return '-';
|
||||
}
|
||||
|
||||
if (
|
||||
didChangeNatureBecauseOfRestrictedRelation &&
|
||||
['oneWay', 'manyWay'].includes(targetContentTypeAllowedRelations[0])
|
||||
) {
|
||||
return '-';
|
||||
}
|
||||
|
||||
return pluralize(
|
||||
snakeCase(oneThatIsCreatingARelationWithAnother),
|
||||
shouldPluralizeTargetAttribute(obj.get('nature'))
|
||||
);
|
||||
});
|
||||
}
|
||||
|
||||
return obj.updateIn(keys, () => value);
|
||||
});
|
||||
case 'ON_CHANGE_ALLOWED_TYPE': {
|
||||
if (action.name === 'all') {
|
||||
return state.updateIn(['modifiedData', 'allowedTypes'], () => {
|
||||
if (action.value) {
|
||||
return fromJS(['images', 'videos', 'files']);
|
||||
return pluralize(
|
||||
snakeCase(oneThatIsCreatingARelationWithAnother),
|
||||
shouldPluralizeTargetAttribute(obj.get('nature'))
|
||||
);
|
||||
});
|
||||
}
|
||||
|
||||
return null;
|
||||
});
|
||||
return obj.updateIn(keys, () => value);
|
||||
})
|
||||
.toJS();
|
||||
case ON_CHANGE_ALLOWED_TYPE: {
|
||||
if (action.name === 'all') {
|
||||
return state
|
||||
.updateIn(['modifiedData', 'allowedTypes'], () => {
|
||||
if (action.value) {
|
||||
return fromJS(['images', 'videos', 'files']);
|
||||
}
|
||||
|
||||
return null;
|
||||
})
|
||||
.toJS();
|
||||
}
|
||||
|
||||
return state.updateIn(['modifiedData', 'allowedTypes'], currentList => {
|
||||
@ -164,15 +185,15 @@ const reducer = (state, action) => {
|
||||
return list.push(action.name);
|
||||
});
|
||||
}
|
||||
case 'RESET_PROPS':
|
||||
case RESET_PROPS:
|
||||
return initialState;
|
||||
case 'RESET_PROPS_AND_SET_FORM_FOR_ADDING_AN_EXISTING_COMPO': {
|
||||
case RESET_PROPS_AND_SET_FORM_FOR_ADDING_AN_EXISTING_COMPO: {
|
||||
// This is run when the user doesn't want to create a new component
|
||||
return initialState.update('modifiedData', () =>
|
||||
fromJS({ type: 'component', repeatable: true })
|
||||
);
|
||||
return fromJS(initialState)
|
||||
.update('modifiedData', () => fromJS({ type: 'component', repeatable: true }))
|
||||
.toJS();
|
||||
}
|
||||
case 'RESET_PROPS_AND_SAVE_CURRENT_DATA': {
|
||||
case RESET_PROPS_AND_SAVE_CURRENT_DATA: {
|
||||
// This is run when the user has created a new component
|
||||
const componentToCreate = state.getIn(['modifiedData', 'componentToCreate']);
|
||||
const modifiedData = fromJS({
|
||||
@ -185,27 +206,31 @@ const reducer = (state, action) => {
|
||||
),
|
||||
});
|
||||
|
||||
return initialState
|
||||
return fromJS(initialState)
|
||||
.update('componentToCreate', () => componentToCreate)
|
||||
.update('modifiedData', () => modifiedData)
|
||||
.update('isCreatingComponentWhileAddingAField', () =>
|
||||
state.getIn(['modifiedData', 'createComponent'])
|
||||
);
|
||||
)
|
||||
.toJS();
|
||||
}
|
||||
case 'RESET_PROPS_AND_SET_THE_FORM_FOR_ADDING_A_COMPO_TO_A_DZ': {
|
||||
case RESET_PROPS_AND_SET_THE_FORM_FOR_ADDING_A_COMPO_TO_A_DZ: {
|
||||
const createdDZ = state.get('modifiedData');
|
||||
const dataToSet = createdDZ
|
||||
.set('createComponent', true)
|
||||
.set('componentToCreate', fromJS({ type: 'component' }));
|
||||
|
||||
return initialState.update('modifiedData', () => dataToSet);
|
||||
return fromJS(initialState)
|
||||
.update('modifiedData', () => dataToSet)
|
||||
.toJS();
|
||||
}
|
||||
case 'SET_DATA_TO_EDIT': {
|
||||
case SET_DATA_TO_EDIT: {
|
||||
return state
|
||||
.updateIn(['modifiedData'], () => fromJS(action.data))
|
||||
.updateIn(['initialData'], () => fromJS(action.data));
|
||||
.updateIn(['initialData'], () => fromJS(action.data))
|
||||
.toJS();
|
||||
}
|
||||
case 'SET_ATTRIBUTE_DATA_SCHEMA': {
|
||||
case SET_ATTRIBUTE_DATA_SCHEMA: {
|
||||
const {
|
||||
attributeType,
|
||||
isEditing,
|
||||
@ -218,7 +243,8 @@ const reducer = (state, action) => {
|
||||
if (isEditing) {
|
||||
return state
|
||||
.update('modifiedData', () => fromJS(modifiedDataToSetForEditing))
|
||||
.update('initialData', () => fromJS(modifiedDataToSetForEditing));
|
||||
.update('initialData', () => fromJS(modifiedDataToSetForEditing))
|
||||
.toJS();
|
||||
}
|
||||
|
||||
let dataToSet;
|
||||
@ -268,20 +294,21 @@ const reducer = (state, action) => {
|
||||
dataToSet = { type: attributeType, default: null };
|
||||
}
|
||||
|
||||
return state.update('modifiedData', () => fromJS(dataToSet));
|
||||
return state.update('modifiedData', () => fromJS(dataToSet)).toJS();
|
||||
}
|
||||
case 'SET_DYNAMIC_ZONE_DATA_SCHEMA': {
|
||||
case SET_DYNAMIC_ZONE_DATA_SCHEMA: {
|
||||
return state
|
||||
.update('modifiedData', () => fromJS(action.attributeToEdit))
|
||||
.update('initialData', () => fromJS(action.attributeToEdit));
|
||||
.update('initialData', () => fromJS(action.attributeToEdit))
|
||||
.toJS();
|
||||
}
|
||||
|
||||
case 'SET_ERRORS':
|
||||
return state.update('formErrors', () => fromJS(action.errors));
|
||||
case SET_ERRORS:
|
||||
return state.update('formErrors', () => fromJS(action.errors)).toJS();
|
||||
default:
|
||||
return state;
|
||||
return state.toJS();
|
||||
}
|
||||
};
|
||||
|
||||
export default reducer;
|
||||
export default formModalReducer;
|
||||
export { initialState };
|
||||
|
||||
@ -0,0 +1,24 @@
|
||||
import { createSelector } from 'reselect';
|
||||
import pluginId from '../../pluginId';
|
||||
import { initialState } from './reducer';
|
||||
|
||||
/**
|
||||
* Direct selector to the formModal state domain
|
||||
*/
|
||||
const formModalDomain = () => state => state.get(`${pluginId}_formModal`) || initialState;
|
||||
|
||||
/**
|
||||
* Other specific selectors
|
||||
*/
|
||||
|
||||
/**
|
||||
* Default selector used by formModal
|
||||
*/
|
||||
|
||||
const makeSelectFormModal = () =>
|
||||
createSelector(formModalDomain(), substate => {
|
||||
return substate;
|
||||
});
|
||||
|
||||
export default makeSelectFormModal;
|
||||
export { formModalDomain };
|
||||
@ -28,6 +28,8 @@ describe('CTB | containers | FormModal | reducer | actions', () => {
|
||||
})
|
||||
);
|
||||
|
||||
console.log(expected.toJS());
|
||||
|
||||
expect(reducer(state, action)).toEqual(expected);
|
||||
});
|
||||
|
||||
|
||||
@ -15,11 +15,13 @@ import lifecycles from './lifecycles';
|
||||
import trads from './translations';
|
||||
import pluginPermissions from './permissions';
|
||||
import pluginId from './pluginId';
|
||||
import reducers from './reducers';
|
||||
|
||||
export default strapi => {
|
||||
const pluginDescription = pluginPkg.strapi.description || pluginPkg.description;
|
||||
const icon = pluginPkg.strapi.icon;
|
||||
const name = pluginPkg.strapi.name;
|
||||
|
||||
const plugin = {
|
||||
blockerComponent: null,
|
||||
blockerComponentProps: {},
|
||||
@ -54,6 +56,7 @@ export default strapi => {
|
||||
name,
|
||||
pluginLogo,
|
||||
preventComponentRendering: false,
|
||||
reducers,
|
||||
trads,
|
||||
menu: {
|
||||
pluginsSectionLinks: [
|
||||
|
||||
@ -0,0 +1,8 @@
|
||||
import formModalReducer from './containers/FormModal/reducer';
|
||||
import pluginId from './pluginId';
|
||||
|
||||
const reducers = {
|
||||
[`${pluginId}_formModal`]: formModalReducer,
|
||||
};
|
||||
|
||||
export default reducers;
|
||||
Loading…
x
Reference in New Issue
Block a user