merge refactor/february-2022-pt.1

This commit is contained in:
Chika 2022-02-03 15:56:32 +03:00
parent 40594d377b
commit 1e1422f723
163 changed files with 1779 additions and 2744 deletions

View File

@ -1,3 +1,3 @@
schema:
- ./src/core/graphql/schemas/crm.graphql
- ./src/core/services/CrmService/graphql/schema.graphql
documents: src/**/*.{graphql,js,ts,jsx,tsx}

View File

@ -3,8 +3,8 @@ module.exports = {
service: {
name: 'crmgraphql',
url: 'http://localhost/crmgraphql/',
// localSchemaFile: 'src/core/graphql/schemas/crm.graphql',
// localSchemaFile: 'src/core/services/CrmService/graphql/schema.graphql',
},
excludes: ['src/core/graphql/schemas/**/*.*'],
excludes: ['src/core/services/CrmService/graphql/schema.graphql'],
},
};

View File

@ -26,8 +26,7 @@
"rebass": "^4.0.7",
"styled-components": "^5.2.3",
"typescript": "^4.5.4",
"use-debounce": "^6.0.1",
"validator": "^13.5.2"
"use-debounce": "^6.0.1"
},
"devDependencies": {
"@storybook/addon-actions": "^6.2.9",
@ -61,7 +60,7 @@
},
"scripts": {
"graphql:codegen": "apollo client:codegen --target typescript",
"graphql:update-schema": "apollo client:download-schema src/core/graphql/schemas/crm.graphql",
"graphql:update-schema": "apollo client:download-schema src/core/services/CrmService/graphql/schema.graphql",
"test": "react-scripts test",
"eject": "react-scripts eject",
"start": "dotenv -e .env craco start",

View File

@ -1,7 +0,0 @@
import { lazy } from 'react';
const Content = lazy(() => import('./Content'));
const ELT = () => <Content />;
export default ELT;

View File

@ -3,7 +3,7 @@ import Button from 'client/Elements/Button';
import { openNotification } from 'client/Elements/Notification';
import { useStores } from 'client/hooks/useStores';
import { Process } from 'core/types/Calculation/Store/process';
import { ElementStatus } from 'core/types/statuses';
import { ElementStatus } from 'types/elements';
const BottomControls = ({ insType, onSelectRow, selectedKey }) => {
const { calculationStore } = useStores();

View File

@ -3,8 +3,8 @@ import Button from 'client/Elements/Button';
import { PrimaryText } from 'client/Elements/Text';
import { useStores } from 'client/hooks/useStores';
import { Flex } from 'client/UIKit/grid';
import { ElementStatus } from 'core/types/statuses';
import { useState } from 'react';
import { ElementStatus } from 'types/elements';
import { resetIns } from '../../lib/resetIns';
import validate from '../../lib/validation';

View File

@ -1,5 +1,5 @@
import InsTable from '../InsTable';
import tableConfig from '../lib/config/table';
import InsTable from './index';
export default {
title: 'Components/Calculation/ELT/Kasko',

View File

@ -1,6 +1,6 @@
import { InsTableColumn } from 'client/Components/Calculation/ELT/Content/lib/config/table';
import { Outlined } from 'client/Components/Spinner';
import { formatMoney } from 'core/tools/format';
import { InsTableColumn } from '../../../lib/config/table';
const columns: InsTableColumn[] = [
{

View File

@ -1,7 +1,4 @@
import {
ElementsNames,
TElements,
} from 'core/types/Calculation/Store/elements';
import { ElementsNames } from 'client/Containers/Calculation/types/elements';
import { ValidationCondition } from 'core/validation/validate';
export const requiredFields: ElementsNames[] = [
@ -19,7 +16,7 @@ export const requiredFields: ElementsNames[] = [
'radioInfuranceOPF',
];
export const conditions: TElements<ValidationCondition> = {
export const conditions: Partial<Record<ElementsNames, ValidationCondition>> = {
selectLeaseObjectType: calculationStore => {
const leaseObjectType = calculationStore.getOption('selectLeaseObjectType');
if (leaseObjectType?.evo_id && ['11'].includes(leaseObjectType?.evo_id)) {

View File

@ -1,6 +1,6 @@
import { IAccount } from 'core/services/CrmService/types/entities';
import { currentDate } from 'core/tools/date';
import { ICalculationStore } from 'core/types/Calculation/Store';
import { IAccount } from 'core/types/Entities/crmEntities';
import { get, isNull } from 'lodash';
const mapCategory = {

View File

@ -1,6 +1,6 @@
import { InsTableColumn } from 'client/Components/Calculation/ELT/Content/lib/config/table';
import { Outlined } from 'client/Components/Spinner';
import { formatMoney } from 'core/tools/format';
import { InsTableColumn } from '../../../lib/config/table';
const columns: InsTableColumn[] = [
{

View File

@ -1,7 +1,4 @@
import {
ElementsNames,
TElements,
} from 'core/types/Calculation/Store/elements';
import { ElementsNames } from 'client/Containers/Calculation/types/elements';
import { ValidationCondition } from 'core/validation/validate';
import { omit } from 'lodash';
import { conditions as kaskoConditions } from '../../Kasko/lib/validation';
@ -22,7 +19,7 @@ export const requiredFields: ElementsNames[] = [
'radioInfuranceOPF',
];
const osagoConditions: TElements<ValidationCondition> = {
const osagoConditions: Partial<Record<ElementsNames, ValidationCondition>> = {
selectTownRegistration: calculationStore => {
const objectRegistration = calculationStore.getValue('objectRegistration');
if (objectRegistration === 100000001) {

View File

@ -1,7 +1,7 @@
import axios from 'axios';
import { IAccount } from 'core/services/CrmService/types/entities';
import ELTService from 'core/services/ELTService';
import { ICalculationStore } from 'core/types/Calculation/Store';
import { IAccount } from 'core/types/Entities/crmEntities';
import { toJS } from 'mobx';
import { map_evo_id_elt_FieldName } from '../lib/resetIns';

View File

@ -1,5 +1,5 @@
import { CRMEntity } from 'core/services/CrmService/types/entities';
import { ICalculationStore } from 'core/types/Calculation/Store';
import { TCRMEntity } from 'core/types/Entities/crmEntities';
import { pick } from 'lodash';
import { sources } from './requests';
@ -40,7 +40,7 @@ export function initIns(this: ICalculationStore, insType) {
return;
}
const { ELTStore } = this.stores;
const list: TCRMEntity[] = [];
const list: CRMEntity[] = [];
const evo_id_elt_fieldName = map_evo_id_elt_FieldName[insType](this);
insuranceCompanies.forEach(company => {
if (
@ -60,7 +60,7 @@ export function resetIns(this: ICalculationStore, insType) {
const { ELTStore } = this.stores;
const list: TCRMEntity[] = [];
const list: CRMEntity[] = [];
ELTStore[insType].list.forEach(x => {
const picked = pick(x, initFields, '');
list.push(picked);

View File

@ -1,30 +1,27 @@
import { getTitle } from 'client/Containers/Calculation/lib/elements/tools';
import { getTitle } from 'client/Containers/Calculation/Elements/tools';
import { ElementsNames } from 'client/Containers/Calculation/types/elements';
import { openNotification } from 'client/Elements/Notification';
import { pipe } from 'core/tools/func';
import { ICalculationStore } from 'core/types/Calculation/Store';
import {
ElementsNames,
TElements,
} from 'core/types/Calculation/Store/elements';
import CONDITIONS from 'core/validation/conditions';
import {
convertToValidationResult,
getValue,
showValidationMessages,
validate,
ValidationCondition,
ValidationCondition
} from 'core/validation/validate';
type ELTValidation = {
requiredFields: ElementsNames[];
conditions?: TElements<ValidationCondition>;
conditions?: Partial<Record<ElementsNames, ValidationCondition>>;
};
export default function (this: ICalculationStore, validation: ELTValidation) {
const { requiredFields, conditions: customConditions } = validation;
const requiredFieldsConditions = requiredFields.reduce(
(ac: TElements<ValidationCondition>, elementName) => {
(ac: Partial<Record<ElementsNames, ValidationCondition>>, elementName) => {
ac[elementName] = pipe(
getValue,
CONDITIONS.IS_NULL,

View File

@ -1,4 +1,4 @@
import { IGroup } from 'core/types/Calculation/components';
import { IGroup } from '../../types/common';
export const controlsList: IGroup[] = [
{

View File

@ -1,4 +1,4 @@
import { ISection } from 'core/types/Calculation/components';
import { ISection } from '../../types/common';
export const calculationResults: ISection[] = [
{

View File

@ -1,5 +1,5 @@
import Background from 'client/Elements/Background';
import { renderSections } from '../lib/renderSections';
import { renderSections } from '../../lib/renderSections';
import sectionsList from './sectionsList';
const Sections = props => (

View File

@ -1,60 +1,6 @@
import { ISection } from 'core/types/Calculation/components';
import { ISection } from '../../types/common';
const sections: ISection[] = [
// {
// title: 'Интерес/ЛС',
// groups: [
// {
// title: 'Создание нового интереса в CRM',
// style: { columnsNumber: 3 },
// blocks: [
// {
// elements: [
// 'selectChannel',
// 'tbxNewClient',
// 'selectAccount',
// 'tbxINN',
// 'tbxKPP',
// ],
// },
// {
// elements: [
// 'selectContactClient',
// 'tbxContact',
// 'radioContactGender',
// 'tbxPhoneNumber',
// 'tbxEmailAddress',
// ],
// },
// {
// elements: [
// 'selectSupplier',
// 'selectFinDepartment',
// 'selectBroker',
// 'selectAgent',
// 'selectDoubleAgent',
// ],
// },
// ],
// },
// {
// style: { columnsNumber: 1 },
// blocks: [
// {
// elements: ['tbxCommentLead'],
// },
// ],
// },
// {
// style: { columnsNumber: 1 },
// blocks: [
// {
// elements: ['btnCreateLead'],
// },
// ],
// },
// ],
// },
{
title: 'Лизинг',
groups: [
@ -305,7 +251,6 @@ const sections: ISection[] = [
'selectGPSModel',
'tbxInsKaskoPriceLeasePeriod',
'cbxWithTrailer',
// 'btnDriversApplication',
],
},
{
@ -402,11 +347,6 @@ const sections: ISection[] = [
blocks: [
{
style: { columnsNumber: 2 },
elementStyle: {
head: {
whiteSpace: 'normal',
},
},
elements: [
// 'cbxLastPaymentRedemption',
'cbxPriceWithDiscount',
@ -445,15 +385,6 @@ const sections: ISection[] = [
// {
// title: 'Без ограничений',
// groups: [
// // {
// // blocks: [
// // {
// // elements: [
// // 'selectUserSession'
// // ],
// // },
// // ],
// // },
// {
// blocks: [
// {

View File

@ -1,11 +1,11 @@
import { observer } from 'mobx-react-lite';
import { useStatus } from 'client/hooks/Calculation/useStatus';
import { useAction } from 'client/hooks/Calculation/useAction';
import { useStatus } from 'client/hooks/Calculation/useStatus';
import { observer } from 'mobx-react-lite';
export default Button => ({ name, actionName, ...props }) =>
export default ({ name, valueName: actionName, Component, ...props }) =>
observer(() => {
const { status } = useStatus(name);
const { action } = useAction({ actionName });
return <Button {...props} status={status} action={action} />;
return <Component {...props} status={status} action={action} />;
});

View File

@ -1,13 +1,8 @@
import { observer } from 'mobx-react-lite';
import { useComputedValue } from 'client/hooks/Calculation/useValue';
import { useStatus } from 'client/hooks/Calculation/useStatus';
import { useComputedValue } from 'client/hooks/Calculation/useValue';
import { observer } from 'mobx-react-lite';
export default Component => ({
name,
computedValueName,
validation,
...props
}) =>
export default ({ name, valueName: computedValueName, Component, ...props }) =>
observer(() => {
const { value } = useComputedValue({
computedValueName,

View File

@ -2,10 +2,10 @@ import { useStatus } from 'client/hooks/Calculation/useStatus';
import { useUrl } from 'client/hooks/Calculation/useUrl';
import { observer } from 'mobx-react-lite';
export default Button => ({ name, urlName, ...props }) =>
export default ({ name, valueName: urlName, Component, ...props }) =>
observer(() => {
const { status } = useStatus(name);
const { url } = useUrl({ urlName });
return <Button status={status} {...props} url={url} />;
return <Component status={status} {...props} url={url} />;
});

View File

@ -0,0 +1,59 @@
import { useTableOptions } from 'client/hooks/Calculation/useOptions';
import { useTableStatus } from 'client/hooks/Calculation/useStatus';
import { useTableValidation } from 'client/hooks/Calculation/useValidation';
import { useTableValue } from 'client/hooks/Calculation/useValue';
import { useStores } from 'client/hooks/useStores';
import { observer } from 'mobx-react-lite';
export default ({ Component: Table, ...props }) => {
const { name: tableName, callbacks } = props;
const ObservedTable = observer(Table);
const { calculationStore } = useStores();
const tableData = calculationStore.tables[tableName];
return () => (
<ObservedTable
{...props}
{...tableData}
withTableValue={withTableValue(callbacks)}
/>
);
};
const withTableValue =
callbacks =>
Component =>
({ tableName, rowIndex, propName, validation, ...props }) =>
observer(() => {
const { value, setCurrentValue } = useTableValue({
tableName,
rowIndex,
propName,
columnCallback: callbacks?.[propName],
});
const { status } = useTableStatus({ tableName, rowIndex, propName });
const { validateStatus, message } = useTableValidation({
tableName,
rowIndex,
propName,
validation,
});
const { options, filter } = useTableOptions({
tableName,
rowIndex,
propName,
});
return (
<Component
{...props}
value={value}
setCurrentValue={setCurrentValue}
status={status}
validateStatus={validateStatus}
message={message}
options={options}
filter={filter}
/>
);
});

View File

@ -1,10 +1,10 @@
import { observer } from 'mobx-react-lite';
import { useStoreValue } from 'client/hooks/Calculation/useValue';
import { useOptions } from 'client/hooks/Calculation/useOptions';
import { useStatus } from 'client/hooks/Calculation/useStatus';
import { useValidation } from 'client/hooks/Calculation/useValidation';
import { useOptions } from 'client/hooks/Calculation/useOptions';
import { useStoreValue } from 'client/hooks/Calculation/useValue';
import { observer } from 'mobx-react-lite';
export default Component => ({ name, valueName, validation, ...props }) =>
export default ({ name, valueName, Component, ...props }) =>
observer(() => {
const { value, setCurrentValue } = useStoreValue({
valueName,
@ -13,7 +13,6 @@ export default Component => ({ name, valueName, validation, ...props }) =>
const { validateStatus, message } = useValidation({
elementName: name,
value,
validation,
});
const { options } = useOptions(name);

View File

@ -0,0 +1,40 @@
import ELT from '../../Components/ELT';
import { CustomComponents, NonValueElementsNames } from '../../types/elements';
import { TableNames } from '../../types/tables';
import components from '../components';
import tables from '../tables';
import buildAction from './buildAction';
import buildComputed from './buildComputed';
import buildLink from './buildLink';
import buildTable from './buildTable';
import buildValue from './buildValue';
const valueElementsBuilders = Object.keys(components).reduce(
(acc, elementName) => {
acc[elementName] = buildValue;
return acc;
},
{},
);
const overrideBuilders: Record<
NonValueElementsNames | TableNames | CustomComponents,
any
> = {
labelLeaseObjectRisk: buildComputed,
tbxInsKaskoPriceLeasePeriod: buildComputed,
labelIrrInfo: buildComputed,
labelRegistrationDescription: buildComputed,
btnCreateKP: buildAction,
btnCalculate: buildAction,
linkDownloadKp: buildLink,
componentElt: () => ELT,
tablePayments: ({ name, Component }) =>
buildTable({ name, Component, ...tables[name] }),
tableInsurance: ({ name, Component }) =>
buildTable({ name, Component, ...tables[name] }),
tableResults: ({ name, Component }) =>
buildTable({ name, Component, ...tables[name] }),
};
export default Object.assign(valueElementsBuilders, overrideBuilders);

View File

@ -1,4 +1,3 @@
import ELT from 'client/Components/Calculation/ELT';
import Button from 'client/Elements/Button';
import Checkbox from 'client/Elements/Checkbox';
import Input from 'client/Elements/Input';
@ -9,29 +8,11 @@ import Radio from 'client/Elements/Radio';
import Select from 'client/Elements/Select';
import Switch from 'client/Elements/Switch';
import Table from 'client/Elements/Table';
import TextArea from 'client/Elements/TextArea';
import { Component } from 'core/types/Calculation/components';
import { TElements } from 'core/types/Calculation/Store/elements';
import { StoreTables } from 'core/types/Calculation/Store/tables';
import { FC } from 'react';
import { AllElementsNames } from '../types/elements';
import { TableNames } from './../types/tables';
const elementsComponents: TElements<Component> = {
selectChannel: Select,
tbxNewClient: Input,
selectAccount: Select,
tbxINN: Input,
tbxKPP: Input,
selectContactClient: Select,
tbxContact: Input,
radioContactGender: Radio,
tbxPhoneNumber: Input,
tbxEmailAddress: Input,
selectSupplier: Select,
selectFinDepartment: Select,
selectBroker: Select,
selectAgent: Select,
selectDoubleAgent: Select,
tbxCommentLead: TextArea,
btnCreateLead: Button,
export default {
selectProduct: Select,
selectClientRisk: Select,
selectClientType: Select,
@ -58,7 +39,6 @@ const elementsComponents: TElements<Component> = {
selectBrand: Select,
selectModel: Select,
selectConfiguration: Select,
labelLeaseObjectRisk: Label,
labelDepreciationGroup: Label,
cbxLeaseObjectUsed: Checkbox,
radioDeliveryTime: Radio,
@ -95,19 +75,15 @@ const elementsComponents: TElements<Component> = {
cbxInsDecentral: Switch,
radioInsKaskoType: Radio,
tbxInsFranchise: InputNumber,
selectInsPeriod: Select,
btnFranschise: Button,
cbxInsUnlimitDrivers: Switch,
tbxInsAgeDrivers: InputNumber,
tbxInsExpDrivers: InputNumber,
tbxINNForCalc: InputNumber,
btnDriversApplication: Button,
selectGPSBrand: Select,
selectGPSModel: Select,
selectRegionRegistration: Select,
selectTownRegistration: Select,
radioInfuranceOPF: Radio,
tbxInsKaskoPriceLeasePeriod: InputNumber,
selectRegistration: Select,
selectInsNSIB: Select,
radioRequirementTelematic: Radio,
@ -125,8 +101,6 @@ const elementsComponents: TElements<Component> = {
cbxQuoteRedemptionGraph: Switch,
tbxQuoteName: Input,
radioQuoteContactGender: Radio,
btnCreateKP: Button,
selectUserSession: Select,
cbxDisableChecks: Switch,
selectTarif: Select,
tbxCreditRate: InputNumber,
@ -138,9 +112,31 @@ const elementsComponents: TElements<Component> = {
selectOpportunity: Select,
selectQuote: Select,
cbxRecalcWithRevision: Checkbox,
btnCalculate: Button,
tbxIRR_Perc: InputNumber,
tbxMileage: InputNumber,
radioCalcType: Radio,
tbxTotalPayments: InputNumber,
radioObjectRegistration: Radio,
selectObjectRegionRegistration: Select,
tbxVehicleTaxInYear: InputNumber,
tbxVehicleTaxInLeasingPeriod: InputNumber,
selectObjectCategoryTax: Select,
selectObjectTypeTax: Select,
radioTypePTS: Radio,
selectLegalClientRegion: Select,
selectLegalClientTown: Select,
selectSubsidy: Select,
selectFuelCard: Select,
labelSubsidySum: Label,
tbxMinPriceChange: InputNumber,
/** Computed Elements */
labelLeaseObjectRisk: Label,
tbxInsKaskoPriceLeasePeriod: InputNumber,
labelIrrInfo: Label,
labelRegistrationDescription: Label,
/** Result Elements */
labelResultTotalGraphwithNDS: Label,
labelResultPlPrice: Label,
labelResultPriceUpPr: Label,
@ -157,31 +153,16 @@ const elementsComponents: TElements<Component> = {
labelResultBonusMPL: Label,
labelResultDopMPLLeasing: Label,
labelResultBonusDopProd: Label,
/** Button Elements */
btnCreateKP: Button,
btnCalculate: Button,
/** Link Elements */
linkDownloadKp: Link,
tbxMileage: InputNumber,
radioCalcType: Radio,
tbxTotalPayments: InputNumber,
componentElt: ELT,
radioObjectRegistration: Radio,
selectObjectRegionRegistration: Select,
tbxVehicleTaxInYear: InputNumber,
tbxVehicleTaxInLeasingPeriod: InputNumber,
selectObjectCategoryTax: Select,
selectObjectTypeTax: Select,
radioTypePTS: Radio,
labelRegistrationDescription: Label,
selectLegalClientRegion: Select,
selectLegalClientTown: Select,
selectSubsidy: Select,
selectFuelCard: Select,
labelSubsidySum: Label,
tbxMinPriceChange: InputNumber,
};
const tablesComponents: StoreTables<Component> = {
tableInsurance: Table,
/** Table Elements */
tablePayments: Table,
tableInsurance: Table,
tableResults: Table,
};
export default Object.assign(elementsComponents, tablesComponents);
} as Record<AllElementsNames | TableNames, FC<any>>;

View File

@ -1,82 +1,13 @@
import DownloadOutlined from '@ant-design/icons/lib/icons/DownloadOutlined';
import InsuranceTag from 'client/Components/Calculation/InsuranceTag';
import Link from 'client/Elements/Link';
import buildTooltip from 'client/Elements/Tooltip';
import { withLink } from 'client/hocs/Calculation';
import { MAX_FRANCHISE } from 'core/constants/stores/Calculation/limits';
import { currentYear } from 'core/tools/date';
import { formatMoney, formatNumber } from 'core/tools/format';
import { pipe } from 'core/tools/func';
import { round } from 'core/tools/num';
import {
validateEmail,
validateInn,
validateKpp,
validatePhone,
} from 'core/tools/validate';
import { ElementProps } from 'core/types/Calculation/components';
import { TElements } from 'core/types/Calculation/Store/elements';
import { ElementProps } from 'types/elements';
import { AllElementsNames, ElementsNames } from '../../types/elements';
const elementsProps: TElements<ElementProps> = {
selectChannel: {
showSearch: true,
},
selectAccount: {
showSearch: true,
},
tbxINN: {
validation: {
errorMessage: 'Некорректный ИНН',
validator: validateInn,
},
},
tbxKPP: {
validation: {
errorMessage: 'Некорректный КПП',
validator: validateKpp,
},
},
selectContactClient: {
showSearch: true,
},
radioContactGender: {
style: 'button',
},
tbxPhoneNumber: {
type: 'tel',
validation: {
errorMessage: 'Некорректный номер телефона',
validator: validatePhone,
},
//TODO: mask + 7(999) 999 99 99
},
tbxEmailAddress: {
type: 'email',
//TODO email mask
validation: {
errorMessage: 'Некорректный E-mail',
validator: validateEmail,
},
},
selectSupplier: {
showSearch: true,
},
selectFinDepartment: {
showSearch: false,
},
selectBroker: {
showSearch: false,
},
selectAgent: {
showSearch: true,
},
selectDoubleAgent: {
showSearch: true,
},
btnCreateLead: {
type: 'primary',
text: 'Создать интерес',
},
const elementsProps: Partial<Record<AllElementsNames, ElementProps>> = {
tbxLeaseObjectPrice: {
min: '1000.00',
max: '1000000000.00',
@ -152,7 +83,6 @@ const elementsProps: TElements<ElementProps> = {
min: '50',
max: '99',
},
selectSeasonType: {},
tbxComissionPerc: {
min: '0',
max: '100',
@ -278,10 +208,6 @@ const elementsProps: TElements<ElementProps> = {
precision: 2,
formatter: formatNumber,
},
btnFranschise: {
type: 'ghost',
text: 'Заявление на франшизу',
},
tbxInsAgeDrivers: {
min: '18',
max: '99',
@ -290,19 +216,12 @@ const elementsProps: TElements<ElementProps> = {
min: '0',
max: '99',
},
btnDriversApplication: {
type: 'ghost',
text: 'Заявление на ограничения по водителям',
},
selectRegionRegistration: {
showSearch: true,
},
selectTownRegistration: {
showSearch: true,
},
radioRequirementTelematic: {
// style: 'button',
},
radioQuoteContactGender: {
style: 'button',
},
@ -334,36 +253,12 @@ const elementsProps: TElements<ElementProps> = {
},
selectLead: {
showSearch: true,
sub: {
Component: withLink(Link)({
name: 'leadUrl',
text: 'Открыть в CRM',
urlName: 'leadUrl',
type: 'link',
}),
},
},
selectOpportunity: {
showSearch: true,
sub: {
Component: withLink(Link)({
name: 'leadUrl',
text: 'Открыть в CRM',
urlName: 'opportunityUrl',
type: 'link',
}),
},
},
selectQuote: {
showSearch: true,
sub: {
Component: withLink(Link)({
name: 'leadUrl',
text: 'Открыть в CRM',
urlName: 'quoteUrl',
type: 'link',
}),
},
},
btnCalculate: {
text: 'Рассчитать график',
@ -402,9 +297,6 @@ const elementsProps: TElements<ElementProps> = {
precision: 2,
formatter: formatNumber,
},
componentElt: {
title: 'Расчет страховки в ЭЛТ',
},
radioObjectRegistration: {
style: 'button',
},
@ -416,12 +308,6 @@ const elementsProps: TElements<ElementProps> = {
step: '100',
max: '9999999',
precision: 2,
tooltip: {
Component: buildTooltip({
title: 'Без учета налога на роскошь',
placement: 'topLeft',
}),
},
},
tbxVehicleTaxInLeasingPeriod: {
min: '0',
@ -432,21 +318,12 @@ const elementsProps: TElements<ElementProps> = {
selectObjectRegionRegistration: {
showSearch: true,
},
tbxINNForCalc: {
// validation: {
// errorMessage: 'Некорректный ИНН',
// validator: validateInn,
// },
},
tableInsurance: {
sub: {
Component: InsuranceTag,
},
},
tbxInsKaskoPriceLeasePeriod: {
min: 0,
precision: 2,
formatter: formatNumber,
readOnly: true,
controls: false,
},
selectLegalClientRegion: {
showSearch: true,
@ -457,31 +334,21 @@ const elementsProps: TElements<ElementProps> = {
radioInfuranceOPF: {
style: 'button',
},
selectHighSeasonStart: {
tooltip: {
Component: buildTooltip({
title: 'С какого платежа начинается полный высокий сезон',
placement: 'topLeft',
}),
},
},
};
export const numberElementsProps: TElements<ElementProps> = Object.keys(
elementsProps,
).reduce((acc, a) => {
const min = elementsProps[a]?.min,
max = elementsProps[a]?.max;
if (min || max)
return {
...acc,
[a]: { min, max },
};
return acc;
}, {});
export const numberElementsProps: Partial<Record<ElementsNames, ElementProps>> =
Object.keys(elementsProps).reduce((acc, a) => {
const min = elementsProps[a]?.min,
max = elementsProps[a]?.max;
if (min || max)
return {
...acc,
[a]: { min, max },
};
return acc;
}, {});
const labelElementsProps: TElements<ElementProps> = Object.assign(
{},
const moneyResultElementsProps = (
[
'labelResultTotalGraphwithNDS',
'labelResultPlPrice',
@ -496,25 +363,33 @@ const labelElementsProps: TElements<ElementProps> = Object.assign(
'labelResultDopMPLLeasing',
'labelResultBonusDopProd',
'labelSubsidySum',
].reduce(
(ac, a) => ({
...ac,
//@ts-ignore
[a]: { middleware: value => pipe(round, formatMoney)(value) },
}),
{},
),
] as ElementsNames[]
).reduce(
(ac, a) => ({
...ac,
//@ts-ignore
[a]: { middleware: value => pipe(round, formatMoney)(value) },
}),
{},
);
const numberResultElementsProps = (
[
'labelResultPriceUpPr',
'labelResultIRRGraphPerc',
'labelResultIRRNominalPerc',
'labelResultTerm',
].reduce(
(ac, a) => ({
...ac,
[a]: { middleware: value => round(value) },
}),
{},
),
] as ElementsNames[]
).reduce(
(ac, a) => ({
...ac,
[a]: { middleware: value => round(value) },
}),
{},
);
export default Object.assign(
elementsProps,
moneyResultElementsProps,
numberResultElementsProps,
);
export default Object.assign(elementsProps, labelElementsProps);

View File

@ -0,0 +1,135 @@
import Link from 'client/Elements/Link';
import buildTooltip from 'client/Elements/Tooltip';
import { Flex } from 'client/UIKit/grid';
import { ElementProps } from 'types/elements';
import InsuranceTag from '../../Components/InsuranceTag';
import { AllElementsNames } from '../../types/elements';
import { TableNames } from '../../types/tables';
import buildLink from '../builders/buildLink';
const Head = props => (
<Flex
flexDirection={['column', 'row']}
justifyContent={['', 'space-between']}
alignItems={['', 'center']}
>
{props.children}
</Flex>
);
export default {
selectLead: {
render: (Title, Element) => {
const SubComponent = buildLink({
name: 'leadUrl',
text: 'Открыть в CRM',
valueName: 'leadUrl',
type: 'link',
Component: Link,
});
return (
<Flex flexDirection="column">
<Head>
<Title />
<SubComponent />
</Head>
<Element />
</Flex>
);
},
},
selectOpportunity: {
render: (Title, Element) => {
const SubComponent = buildLink({
name: 'leadUrl',
text: 'Открыть в CRM',
valueName: 'opportunityUrl',
type: 'link',
Component: Link,
});
return (
<Flex flexDirection="column">
<Head>
<Title />
<SubComponent />
</Head>
<Element />
</Flex>
);
},
},
selectQuote: {
render: (Title, Element) => {
const SubComponent = buildLink({
name: 'leadUrl',
text: 'Открыть в CRM',
valueName: 'quoteUrl',
type: 'link',
Component: Link,
});
return (
<Flex flexDirection="column">
<Head>
<Title />
<SubComponent />
</Head>
<Element />
</Flex>
);
},
},
tableInsurance: {
sub: {
Component: InsuranceTag,
},
render: (Title, Element) => {
return (
<Flex flexDirection="column">
<Head>
<Title />
<InsuranceTag />
</Head>
<Element />
</Flex>
);
},
},
tbxVehicleTaxInYear: {
render: (Title, Component) => {
const Tooltip = buildTooltip({
title: 'Без учета налога на роскошь',
placement: 'topLeft',
});
return (
<Tooltip>
<Flex flexDirection="column">
<Title />
<Component />
</Flex>
</Tooltip>
);
},
},
selectHighSeasonStart: {
render: (Title, Component) => {
const Tooltip = buildTooltip({
title: 'С какого платежа начинается полный высокий сезон',
placement: 'topLeft',
});
return (
<Tooltip>
<Flex flexDirection="column">
<Title />
<Component />
</Flex>
</Tooltip>
);
},
},
} as Partial<Record<AllElementsNames | TableNames, ElementProps>>;

View File

@ -8,16 +8,10 @@ import {
} from 'core/constants/stores/Calculation/filters';
import { MAX_INSURANCE } from 'core/constants/stores/Calculation/limits';
import { formatNumber } from 'core/tools/format';
import {
ITable,
TableColumn,
TableColumnCallbacks,
TableColumnOptions,
TableRow,
} from 'core/types/Calculation/Store/tables';
import { ElementStatus } from 'core/types/statuses';
import { ElementStatus } from 'types/elements';
import { Column, Table } from '../../types/tables';
const columns: TableColumn[] = [
const columns: Column[] = [
{
name: 'policyType',
title: 'Тип полиса',
@ -61,7 +55,7 @@ const columns: TableColumn[] = [
},
];
const rows: TableRow[] = [
const rows: Table['rows'] = [
{
policyType: {
value: 'ОСАГО',
@ -144,7 +138,7 @@ const rows: TableRow[] = [
},
];
const callbacks: TableColumnCallbacks = {
const callbacks: Table['callbacks'] = {
insCost: ({ calculationStore, tableName, rowIndex }) => {
if (
calculationStore.tables[tableName]?.rows[rowIndex]['insCost']?.value &&
@ -336,7 +330,7 @@ const callbacks: TableColumnCallbacks = {
},
};
const options: TableColumnOptions = {
const options: Table['options'] = {
insured: [
{
name: 'ЛП',
@ -365,4 +359,4 @@ export default {
options,
callbacks,
params: {},
} as ITable;
} as Table;

View File

@ -2,16 +2,12 @@ import InputNumber from 'client/Elements/InputNumber';
import valuesConstants from 'core/constants/values';
import { rotateArrays } from 'core/tools/array';
import { formatNumber } from 'core/tools/format';
import {
ITable,
TableColumn,
TableColumnCallbacks,
TableColumnFeatures,
} from 'core/types/Calculation/Store/tables';
import { inRange } from 'lodash';
import { Table } from '../../types/tables';
const { PERIODS_NUMBER } = valuesConstants;
const columns: TableColumn[] = [
const columns: Table['columns'] = [
{
name: 'paymentRelation',
title: '% платежа',
@ -26,7 +22,7 @@ const columns: TableColumn[] = [
},
];
const callbacks: TableColumnCallbacks = {
const callbacks: Table['callbacks'] = {
paymentRelation: ({ calculationStore, tableName, rowIndex, value }) => {
const rowLength = calculationStore.tables[tableName].rows.length;
const { graphType, seasonType } = calculationStore.values;
@ -65,9 +61,8 @@ const callbacks: TableColumnCallbacks = {
),
shiftNumber = highSeasonStartValue - 2;
const seasonTypeOptions = calculationStore.getOption(
'selectSeasonType',
);
const seasonTypeOptions =
calculationStore.getOption('selectSeasonType');
const startPositions =
seasonTypeOptions && seasonTypeOptions.startPositions,
endPositions =
@ -123,19 +118,19 @@ const callbacks: TableColumnCallbacks = {
},
};
const features: TableColumnFeatures = {
numerize: true,
split: {
rowsNumber: 12,
columnsNumber: 3,
const params: Table['params'] = {
features: {
numerize: true,
split: {
rowsNumber: 12,
columnsNumber: 3,
},
},
};
const params = { features };
export default {
columns,
rows: [],
params,
callbacks,
} as ITable;
} as Table;

View File

@ -3,13 +3,9 @@ import Label from 'client/Elements/Label';
import { formatMoney } from 'core/tools/format';
import { pipe } from 'core/tools/func';
import { round } from 'core/tools/num';
import {
ITable,
TableColumn,
TableColumnFeatures,
} from 'core/types/Calculation/Store/tables';
import { Column, Table } from '../../types/tables';
const columns: TableColumn[] = [
const columns: Column[] = [
{
name: 'paymentSum',
title: 'Сумма платежа',
@ -36,14 +32,14 @@ const columns: TableColumn[] = [
},
];
const features: TableColumnFeatures = {
numerize: true,
const params: Table['params'] = {
features: {
numerize: true,
},
};
const params = { features };
export default {
columns,
rows: [],
params,
} as ITable;
} as Table;

View File

@ -1,27 +1,10 @@
import { TElements } from 'core/types/Calculation/Store/elements';
import { StoreTables } from 'core/types/Calculation/Store/tables';
import { AllElementsNames } from '../types/elements';
import { TableNames } from '../types/tables';
export const elementsTitles: TElements<string> = {
export const elementsTitles: Partial<Record<AllElementsNames, string>> = {
selectLead: 'Интерес',
selectOpportunity: 'Лизинговая сделка',
selectQuote: 'Предложение',
selectTemplate: 'Выбор шаблона',
selectChannel: 'Канал привлечения',
tbxNewClient: 'Новый контрагент',
selectAccount: 'Существующий контрагент',
tbxINN: 'ИНН',
tbxKPP: 'КПП',
selectContactClient: 'Контактное лицо контрагента',
tbxContact: 'Контактное лицо',
radioContactGender: 'Пол контактного лица',
tbxPhoneNumber: 'Телефон',
tbxEmailAddress: 'E-mail',
selectSupplier: 'Поставщик',
selectFinDepartment: 'Финотдел',
selectAgent: 'Агент',
selectDoubleAgent: 'Двойной агент',
selectBroker: 'Брокер',
tbxCommentLead: 'Комментарий к интересу',
selectProduct: 'Продукт',
selectClientRisk: 'Риск клиента',
selectClientType: 'Тип клиента',
@ -113,15 +96,12 @@ export const elementsTitles: TElements<string> = {
tbxImporterRewardPerc: 'АВ импортера, %',
tbxImporterRewardRub: 'АВ импортера, руб.',
cbxDisableChecks: 'Отключить все проверки',
tbxSystemUser: 'Пользователь',
tbxBusinessUnit: 'Подразделение',
selectRegistration: 'Регистрация',
selectInsNSIB: 'НСИБ',
selectTechnicalCard: 'Карта техпомощи',
radioRequirementTelematic: 'Программа средства контроля',
selectTelematic: 'Телематика ',
selectTracker: 'Маяк',
selectUserSession: 'Загрузить сессию пользователя',
labelIrrInfo: 'Диапазон IRR (Номинал)',
tbxMileage: 'Пробег, км',
radioCalcType: 'Расчет от',
@ -141,9 +121,8 @@ export const elementsTitles: TElements<string> = {
labelSubsidySum: 'Сумма субсидии с НДС',
selectFuelCard: 'Топливная карта',
tbxMinPriceChange: 'Мин. возможное изменение стоимости ПЛ',
};
const resultsTitles: TElements<string> = {
/** Result Elements */
labelResultTotalGraphwithNDS: 'Итого по графику, с НДС',
labelResultPlPrice: 'Стоимость ПЛ с НДС',
labelResultPriceUpPr: 'Удорожание, год',
@ -162,10 +141,10 @@ const resultsTitles: TElements<string> = {
labelResultBonusDopProd: 'Бонус МПЛ за доп.продукты, без НДФЛ',
};
export const tablesTitles: StoreTables<string> = {
export const tablesTitles: Record<TableNames, string> = {
tableInsurance: 'Таблица страхования',
tablePayments: 'Таблица платежей',
tableResults: '',
};
export default Object.assign(elementsTitles, resultsTitles, tablesTitles);
export default Object.assign(elementsTitles, tablesTitles);

View File

@ -1,17 +1,15 @@
//@ts-nocheck
import { ElementsNames } from 'core/types/Calculation/Store/elements';
import { ValuesNames } from 'core/types/Calculation/Store/values';
import { ElementsNames } from '../types/elements';
import { elementsTitles } from './titles';
import { elementsValues } from './values';
import values from './values';
export function getValueName(elementName: ElementsNames): ValuesNames {
return elementsValues[elementName];
return values[elementName];
}
export function getFieldName(valueName: ValuesNames): ElementsNames {
return Object.keys(elementsValues).find(
key => elementsValues[key] === valueName,
);
return Object.keys(values).find(key => values[key] === valueName);
}
export function getTitle(elementName: ElementsNames): string {

View File

@ -1,31 +1,21 @@
import { TElements } from 'core/types/Calculation/Store/elements';
import { ActionsNames } from 'core/types/Calculation/Store/effect';
import { LinksNames } from 'core/types/Calculation/Store/links';
import {
ResultValuesNames,
ComputedValuesNames,
ValuesNames,
} from 'core/types/Calculation/Store/values';
import {
ButtonElementsNames,
ComputedElementsNames,
ElementsNames,
LinkElementsNames,
} from '../types/elements';
export const elementsValues: TElements<ValuesNames> = {
const elementsValues: Record<ElementsNames, ValuesNames> = {
selectLead: 'lead',
selectOpportunity: 'opportunity',
selectQuote: 'quote',
cbxRecalcWithRevision: 'recalcWithRevision',
selectTemplate: 'template',
selectChannel: 'channel',
tbxNewClient: 'newClient',
selectAccount: 'account',
tbxINN: 'INN',
tbxKPP: 'KPP',
selectContactClient: 'contactClient',
tbxContact: 'contact',
radioContactGender: 'contactGender',
tbxPhoneNumber: 'phoneNumber',
tbxEmailAddress: 'emailAddress',
selectSupplier: 'supplier',
selectFinDepartment: 'finDepartment',
selectAgent: 'agent',
selectDoubleAgent: 'doubleAgent',
selectBroker: 'broker',
tbxCommentLead: 'commentLead',
selectProduct: 'product',
selectClientRisk: 'clientRisk',
selectClientType: 'clientType',
@ -93,7 +83,6 @@ export const elementsValues: TElements<ValuesNames> = {
radioInfuranceOPF: 'infuranceOPF',
radioInsKaskoType: 'insKaskoType',
cbxInsDecentral: 'insDecentral',
selectInsPeriod: 'insPeriod',
tbxInsFranchise: 'insFranchise',
cbxInsUnlimitDrivers: 'insUnlimitDrivers',
tbxInsAgeDrivers: 'insAgeDrivers',
@ -113,7 +102,6 @@ export const elementsValues: TElements<ValuesNames> = {
selectTarif: 'tarif',
tbxCreditRate: 'creditRate',
selectRate: 'rate',
selectUserSession: 'userSession',
tbxMaxPriceChange: 'maxPriceChange',
tbxImporterRewardPerc: 'importerRewardPerc',
tbxImporterRewardRub: 'importerRewardRub',
@ -140,9 +128,8 @@ export const elementsValues: TElements<ValuesNames> = {
labelSubsidySum: 'subsidySum',
selectFuelCard: 'fuelCard',
tbxMinPriceChange: 'minPriceChange',
};
const resultElementsValues: TElements<ResultValuesNames> = {
/** Result Elements */
labelResultTotalGraphwithNDS: 'resultTotalGraphwithNDS',
labelResultPlPrice: 'resultPlPrice',
labelResultPriceUpPr: 'resultPriceUpPr',
@ -161,4 +148,28 @@ const resultElementsValues: TElements<ResultValuesNames> = {
labelResultBonusDopProd: 'resultBonusDopProd',
};
export default Object.assign(elementsValues, resultElementsValues);
const elementsComputedValues: Record<
ComputedElementsNames,
ComputedValuesNames
> = {
labelLeaseObjectRisk: 'leaseObjectRiskName',
tbxInsKaskoPriceLeasePeriod: 'insKaskoPriceLeasePeriod',
labelIrrInfo: 'irrInfo',
labelRegistrationDescription: 'registrationDescription',
};
const elementsActions: Record<ButtonElementsNames, ActionsNames> = {
btnCalculate: 'calculate',
btnCreateKP: 'createKP',
};
const elementsLinks: Record<LinkElementsNames, LinksNames> = {
linkDownloadKp: 'kpUrl',
};
export default Object.assign(
elementsValues,
elementsComputedValues,
elementsActions,
elementsLinks,
);

View File

@ -2,9 +2,9 @@ import withStores from 'client/hocs/withStores';
import { Box } from 'client/UIKit/grid';
import mq from 'client/UIKit/mq';
import styled from 'styled-components';
import Info from './Info';
import Results from './Results';
import Sections from './Sections';
import Info from './Components/Info';
import Results from './Components/Results';
import Sections from './Components/Sections';
const Grid = styled(Box)`
grid-gap: 10px;

View File

@ -1,61 +1,20 @@
import {
withButton,
withComputedValue,
withLink,
withTable,
withValue,
} from 'client/hocs/Calculation';
import { ElementType } from 'core/types/Calculation/Store/elements';
import { pick } from 'lodash';
import elementsActions from './elements/actions';
import elementsComponents from './elements/components';
import elementsComputedValues from './elements/computedValues';
import tables from './elements/tables';
import { getValueName } from './elements/tools';
import elementsTypes from './elements/types';
import elementsUrls from './elements/urls';
import builders from '../Elements/builders';
import components from '../Elements/components';
import props from '../Elements/props/common';
import { getValueName } from '../Elements/tools';
export function buildElement(elementName, elementProps = {}) {
const elementType = elementsTypes[elementName];
const Component = elementsComponents[elementName];
export function buildElement(name) {
const valueName = getValueName(name);
const Component = components[name];
const elementProps = props[name];
switch (elementType) {
case ElementType.Table: {
return withTable(Component)({
name: elementName,
...pick(tables[elementName], ['options', 'callbacks', 'params']),
});
}
case ElementType.Action: {
return withButton(Component)({
name: elementName,
actionName: elementsActions[elementName],
...elementProps,
});
}
case ElementType.Computed: {
return withComputedValue(Component)({
name: elementName,
computedValueName: elementsComputedValues[elementName],
...elementProps,
});
}
case ElementType.Link: {
return withLink(Component)({
name: elementName,
urlName: elementsUrls[elementName],
...elementProps,
});
}
case ElementType.Custom: {
return () => <Component {...elementProps} />;
}
default: {
return withValue(Component)({
name: elementName,
valueName: getValueName(elementName),
...elementProps,
});
}
}
const builder = builders[name];
const Element = builder({
name,
valueName,
Component,
...elementProps,
});
return Element;
}

View File

@ -1,10 +0,0 @@
import { TElements } from 'core/types/Calculation/Store/elements';
import { ActionsNames } from 'core/types/Calculation/Store/effect';
const elementsActions: TElements<ActionsNames> = {
btnCalculate: 'calculate',
btnCreateLead: 'createLead',
btnCreateKP: 'createKP',
};
export default elementsActions;

View File

@ -1,11 +0,0 @@
import { TElements } from 'core/types/Calculation/Store/elements';
import { ComputedValuesNames } from 'core/types/Calculation/Store/values';
const elementsComputedValues: TElements<ComputedValuesNames> = {
labelLeaseObjectRisk: 'leaseObjectRiskName',
tbxInsKaskoPriceLeasePeriod: 'insKaskoPriceLeasePeriod',
labelIrrInfo: 'irrInfo',
labelRegistrationDescription: 'registrationDescription',
};
export default elementsComputedValues;

View File

@ -1,23 +0,0 @@
import { ElementType, TElements } from 'core/types/Calculation/Store/elements';
import { StoreTables } from 'core/types/Calculation/Store/tables';
const elementsTypes: TElements<ElementType> = {
labelLeaseObjectRisk: ElementType.Computed,
btnFranschise: ElementType.Action,
btnDriversApplication: ElementType.Action,
tbxInsKaskoPriceLeasePeriod: ElementType.Computed,
btnCreateKP: ElementType.Action,
btnCalculate: ElementType.Action,
labelIrrInfo: ElementType.Computed,
linkDownloadKp: ElementType.Link,
componentElt: ElementType.Custom,
labelRegistrationDescription: ElementType.Computed,
};
const tablesTypes: StoreTables<ElementType> = {
tablePayments: ElementType.Table,
tableInsurance: ElementType.Table,
tableResults: ElementType.Table,
};
export default Object.assign(elementsTypes, tablesTypes);

View File

@ -1,8 +0,0 @@
import { LinksNames } from 'core/types/Calculation/Store/links';
import { TElements } from 'core/types/Calculation/Store/elements';
const elementsUrls: TElements<LinksNames> = {
linkDownloadKp: 'kpUrl',
};
export default elementsUrls;

View File

@ -5,9 +5,9 @@ import colors from 'client/UIKit/colors';
import { Box, Flex } from 'client/UIKit/grid';
import mq from 'client/UIKit/mq';
import styled from 'styled-components';
import elementsRenderProps from '../Elements/props/render';
import elementsTitles from '../Elements/titles';
import { buildElement } from '../lib/buildElement';
import elementsProps from './elements/elementsProps';
import elementsTitles from './elements/titles';
const ElementTitle = styled.h5`
color: rgba(0, 0, 0, 0.75);
@ -17,47 +17,26 @@ const ElementTitle = styled.h5`
margin: 0 8px 3px 0;
text-overflow: ellipsis;
overflow: hidden;
white-space: ${props => props.whiteSpace || 'nowrap'};
white-space: nowrap;
`;
const Head = ({ sub, elementTitle, style }) => {
if (sub?.Component) {
return (
<Flex
flexDirection={['column', 'row']}
justifyContent={[undefined, 'space-between']}
alignItems={[undefined, 'center']}
>
<ElementTitle {...style}>{elementTitle}</ElementTitle>
<sub.Component />
</Flex>
);
}
return <ElementTitle {...style}>{elementTitle}</ElementTitle>;
};
const renderElements = ({ elements }) => {
return elements.map(elementName => {
const elementTitleText = elementsTitles[elementName];
const Title = () => <ElementTitle>{elementTitleText}</ElementTitle>;
const Element = buildElement(elementName);
const renderElements = ({ elements, elementStyle }) => {
return elements.map((elementName, ie) => {
const elementTitle = elementsTitles[elementName];
const { tooltip, sub, ...elementProps } = elementsProps[elementName] || {};
const Component = buildElement(elementName, elementProps);
const Tooltip = tooltip?.Component;
const element = (
<Flex flexDirection="column" key={ie}>
<Head
sub={sub}
elementTitle={elementTitle}
style={elementStyle?.head}
/>
<Component />
</Flex>
);
if (tooltip) {
return <Tooltip>{element}</Tooltip>;
if (elementsRenderProps[elementName]) {
const { render } = elementsRenderProps[elementName];
return render(Title, Element);
}
return element;
return (
<Flex flexDirection="column" key={elementName}>
<Title />
<Element />
</Flex>
);
});
};
@ -73,16 +52,13 @@ const ElementsGrid = styled(Box)`
`;
const renderBlocks = ({ blocks }) => {
if (!blocks || blocks.length === 0) {
return null;
}
return blocks.map((block, ib) => {
const { elements, title, style, elementStyle } = block;
return blocks?.map((block, ib) => {
const { elements, title, style } = block;
return (
<Flex key={ib} flexDirection="column" flexWrap="nowrap">
{title && <SecondaryColoredText>{title}</SecondaryColoredText>}
<ElementsGrid {...style} defaultColumnsNumber={1}>
{renderElements({ elements, elementStyle })}
{renderElements({ elements })}
</ElementsGrid>
</Flex>
);
@ -96,10 +72,7 @@ const BlocksTitle = styled(Divider)`
`;
export const renderGroups = ({ groups }) => {
if (!groups || groups.length === 0) {
return null;
}
return groups.map((group, ig) => {
return groups?.map((group, ig) => {
const { title, blocks, style } = group;
return (

View File

@ -0,0 +1,19 @@
import { AllElementsNames, CustomComponents } from './elements';
import { TableNames } from './tables';
interface IBlock {
title?: string;
elements: (AllElementsNames | TableNames | CustomComponents)[];
[key: string]: any;
}
export interface IGroup {
title?: string;
blocks?: IBlock[];
style?: { [key: string]: any };
}
export interface ISection {
title?: string;
groups?: IGroup[];
}

View File

@ -1,28 +1,8 @@
import { TableNames } from 'core/types/Calculation/Store/tables';
export type ElementsNames =
| 'selectLead'
| 'selectOpportunity'
| 'selectQuote'
| 'cbxRecalcWithRevision'
| 'selectTemplate'
| 'selectChannel'
| 'tbxNewClient'
| 'selectAccount'
| 'tbxINN'
| 'tbxKPP'
| 'selectContactClient'
| 'tbxContact'
| 'radioContactGender'
| 'tbxPhoneNumber'
| 'tbxEmailAddress'
| 'selectSupplier'
| 'selectFinDepartment'
| 'selectAgent'
| 'selectDoubleAgent'
| 'selectBroker'
| 'tbxCommentLead'
| 'btnCreateLead'
| 'selectProduct'
| 'selectClientRisk'
| 'selectClientType'
@ -48,7 +28,6 @@ export type ElementsNames =
| 'tbxIRR_Perc'
| 'selectLeaseObjectType'
| 'radioDeliveryTime'
| 'labelLeaseObjectRisk'
| 'labelDepreciationGroup'
| 'tbxLeaseObjectCount'
| 'cbxWithTrailer'
@ -90,9 +69,7 @@ export type ElementsNames =
| 'selectTownRegistration'
| 'radioInfuranceOPF'
| 'radioInsKaskoType'
| 'tbxInsKaskoPriceLeasePeriod'
| 'cbxInsDecentral'
| 'selectInsPeriod'
| 'tbxInsFranchise'
| 'cbxInsUnlimitDrivers'
| 'tbxInsAgeDrivers'
@ -108,32 +85,20 @@ export type ElementsNames =
| 'cbxNSIB'
| 'tbxQuoteName'
| 'radioQuoteContactGender'
| 'btnCreateKP'
| 'cbxQuoteRedemptionGraph'
| 'selectTarif'
| 'tbxCreditRate'
| 'selectRate'
| 'selectUserSession'
| 'radioRequirementTelematic'
| 'tbxMaxPriceChange'
| 'tbxImporterRewardPerc'
| 'tbxImporterRewardRub'
| 'cbxDisableChecks'
| 'btnFranschise'
| 'btnDriversApplication'
| 'tbxSystemUser'
| 'tbxBusinessUnit'
| 'tbxLeadNumber'
| 'tbxOpportunityNumber'
| 'lblLead'
| 'lblOpportunity'
| 'btnCalculate'
| 'selectRegistration'
| 'selectInsNSIB'
| 'selectTechnicalCard'
| 'selectTelematic'
| 'selectTracker'
| 'labelIrrInfo'
| 'tbxMileage'
| 'radioCalcType'
| 'tbxTotalPayments'
@ -144,17 +109,13 @@ export type ElementsNames =
| 'selectObjectCategoryTax'
| 'selectObjectTypeTax'
| 'radioTypePTS'
| 'labelRegistrationDescription'
| 'selectLegalClientRegion'
| 'selectLegalClientTown'
| 'selectSubsidy'
| 'labelSubsidySum'
| 'selectFuelCard'
| 'tbxMinPriceChange';
export type LinkElementsNames = 'linkDownloadKp';
export type ResultElementsNames =
| 'tbxMinPriceChange'
/** Result Elements */
| 'labelResultTotalGraphwithNDS'
| 'labelResultPlPrice'
| 'labelResultPriceUpPr'
@ -171,25 +132,29 @@ export type ResultElementsNames =
| 'labelResultBonusMPL'
| 'labelResultDopMPLLeasing'
| 'labelResultBonusDopProd';
export type ButtonElementsNames = 'btnCreateKP' | 'btnCalculate';
export type LinkElementsNames = 'linkDownloadKp';
export type ComputedElementsNames =
| 'labelLeaseObjectRisk'
| 'tbxInsKaskoPriceLeasePeriod'
| 'labelIrrInfo'
| 'labelRegistrationDescription';
export type CustomComponents = 'componentElt';
export type AllElements =
/** GROUPS */
export type InteractionElementsNames =
| ElementsNames
| ResultElementsNames
| ButtonElementsNames
| LinkElementsNames;
export type NonValueElementsNames =
| ButtonElementsNames
| LinkElementsNames
| CustomComponents
| TableNames;
| ComputedElementsNames;
export enum ElementType {
Default,
Computed,
Table,
Action,
Link,
Custom,
}
export type TElements<T> = {
[elementName in AllElements]?: T;
};
export type AllElementsNames =
| ElementsNames
| ComputedElementsNames
| ButtonElementsNames
| LinkElementsNames;

View File

@ -0,0 +1,49 @@
import { TCalculationProcess } from 'client/stores/CalculationStore/subStores/calculationProcess';
import { TOptionizedEntity } from 'core/services/CrmService/types/common';
import { ICalculationStore } from 'core/types/Calculation/Store';
import { TElementFilter } from 'core/types/Calculation/Store/filters';
import { FC } from 'react';
import { ElementProps, ElementStatus } from 'types/elements';
export type TableNames = 'tableInsurance' | 'tablePayments' | 'tableResults';
export type TableValuesNames =
| 'policyType'
| 'insuranceCompany'
| 'insured'
| 'insCost'
| 'insTerm'
| 'paymentNumber'
| 'paymentRelation'
| 'paymentSum'
| 'ndsCompensation'
| 'redemptionAmount';
type CellCallback = (props: {
calculationStore: ICalculationStore;
calculationProcess: TCalculationProcess;
tableName: TableNames;
rowIndex: number;
value: any;
}) => void;
export type Cell = {
value?: any;
status?: ElementStatus;
validation?: boolean;
filter?: TElementFilter;
};
export type Column = {
name: TableValuesNames;
title: string;
Component: FC<any>;
props?: ElementProps;
};
export type Table = {
columns: Column[];
rows: Partial<Record<TableValuesNames, Cell>>[];
options?: Partial<Record<TableValuesNames, TOptionizedEntity[]>>;
params?: { features?: Record<string, any> };
callbacks?: Partial<Record<TableValuesNames, CellCallback>>;
};

View File

@ -1,7 +1,7 @@
import { Button as AntButton } from 'antd';
import { ACTION_DELAY } from 'core/constants/debounce';
import { ElementStatus } from 'core/types/statuses';
import { throttle } from 'lodash';
import { ElementStatus } from 'types/elements';
const Button = ({ status, action, text, ...props }) => {
const throttledAction = action

View File

@ -1,5 +1,5 @@
import { Checkbox as AntCheckbox, Form } from 'antd';
import { ElementStatus } from 'core/types/statuses';
import { ElementStatus } from 'types/elements';
const Checkbox = ({
value,

View File

@ -1,5 +1,5 @@
import { Form, Input as AntInput } from 'antd';
import { ElementStatus } from 'core/types/statuses';
import { ElementStatus } from 'types/elements';
const Input = ({
value,

View File

@ -1,7 +1,7 @@
import { Form, InputNumber as AntInputNumber } from 'antd';
import { Outlined } from 'client/Components/Spinner';
import { ElementStatus } from 'core/types/statuses';
import styled from 'styled-components';
import { ElementStatus } from 'types/elements';
const { Disabled, Loading } = ElementStatus;

View File

@ -1,5 +1,5 @@
import { Button as AntButton } from 'antd';
import { ElementStatus } from 'core/types/statuses';
import { ElementStatus } from 'types/elements';
const Link = ({ status, url, text, icon: Icon, ...props }) => {
return (

View File

@ -1,5 +1,5 @@
import { Form, Radio as AntRadio } from 'antd';
import { ElementStatus } from 'core/types/statuses';
import { ElementStatus } from 'types/elements';
const Radio = ({
value,

View File

@ -1,5 +1,5 @@
import { Form, Select as AntSelect } from 'antd';
import { ElementStatus } from 'core/types/statuses';
import { ElementStatus } from 'types/elements';
const Select = ({
value = null,

View File

@ -1,5 +1,5 @@
import { Form, Switch as AntSwitch } from 'antd';
import { ElementStatus } from 'core/types/statuses';
import { ElementStatus } from 'types/elements';
const Switch = ({
value,

View File

@ -1,5 +1,5 @@
import { Form, Input as AntInput } from 'antd';
import { ElementStatus } from 'core/types/statuses';
import { ElementStatus } from 'types/elements';
const TextArea = ({
value,

View File

@ -1,7 +0,0 @@
import withButton from './withButton';
import withComputedValue from './withComputedValue';
import withLink from './withLink';
import withTable from './withTable';
import withValue from './withValue';
export { withButton, withLink, withValue, withComputedValue, withTable };

View File

@ -1,62 +0,0 @@
import { useTableOptions } from 'client/hooks/Calculation/useOptions';
import { useTableStatus } from 'client/hooks/Calculation/useStatus';
import { useTableValidation } from 'client/hooks/Calculation/useValidation';
import { useTableValue } from 'client/hooks/Calculation/useValue';
import { useStores } from 'client/hooks/useStores';
import { observer } from 'mobx-react-lite';
export default Table => props => {
const { name: tableName, callbacks } = props;
const ObservedTable = observer(Table);
const { calculationStore } = useStores();
const tableData = calculationStore.tables[tableName];
return () => (
<ObservedTable
{...props}
{...tableData}
withTableValue={withTableValue(callbacks)}
/>
);
};
const withTableValue = callbacks => Component => ({
tableName,
rowIndex,
propName,
validation,
...props
}) =>
observer(() => {
const { value, setCurrentValue } = useTableValue({
tableName,
rowIndex,
propName,
columnCallback: callbacks?.[propName],
});
const { status } = useTableStatus({ tableName, rowIndex, propName });
const { validateStatus, message } = useTableValidation({
tableName,
rowIndex,
propName,
validation,
});
const { options, filter } = useTableOptions({
tableName,
rowIndex,
propName,
});
return (
<Component
{...props}
value={value}
setCurrentValue={setCurrentValue}
status={status}
validateStatus={validateStatus}
message={message}
options={options}
filter={filter}
/>
);
});

View File

@ -0,0 +1,62 @@
import { INVALID_INPUT as INVALID_INPUT_MESSAGE } from 'core/constants/errorMessages';
import { useEffect, useState } from 'react';
import { useStores } from '../useStores';
export const useValidation = ({ elementName, value }) => {
const [isValid, setValidation] = useState(undefined);
const { calculationStore } = useStores();
// get value from store
const validationStatus = calculationStore.validations[elementName];
useEffect(() => {
setValidation(validationStatus);
}, [validationStatus]);
useEffect(() => {
if (value === undefined || value === '') {
calculationStore.setValidation(elementName, undefined);
}
}, [value]);
return {
validateStatus: isValid === false ? 'error' : undefined,
message: isValid === false ? INVALID_INPUT_MESSAGE : undefined,
};
};
export const useTableValidation = ({
tableName,
rowIndex,
propName,
value,
}) => {
const [isValid, setValidation] = useState(undefined);
const { calculationStore } = useStores();
const validationStatus =
calculationStore?.tables?.[tableName]?.rows?.[rowIndex]?.[propName]
?.validation;
useEffect(() => {
setValidation(validationStatus);
}, [validationStatus]);
useEffect(() => {
if (value === undefined || value === '') {
calculationStore.setTableRows(
tableName,
rowIndex,
)([
{
[propName]: {
validation: undefined,
},
},
]);
}
}, [value]);
return {
validateStatus: isValid === false ? 'error' : undefined,
message: isValid === false ? INVALID_INPUT_MESSAGE : undefined,
};
};

View File

@ -1,147 +0,0 @@
import { ValidateStatus } from 'antd/lib/form/FormItem';
import { INVALID_INPUT as INVALID_INPUT_MESSAGE } from 'core/constants/errorMessages';
import { ElementsNames } from 'core/types/Calculation/Store/elements';
import {
TableNames,
TableValuesNames,
} from 'core/types/Calculation/Store/tables';
import { useEffect, useState } from 'react';
import { useStores } from '../useStores';
type TValidation = {
errorMessage: string;
validator: ((_: any) => boolean) | undefined;
};
interface IUseValidationArgs {
elementName: ElementsNames;
value: any;
validation: TValidation;
}
interface IUseTableValidationArgs {
tableName: TableNames;
rowIndex: number;
propName: TableValuesNames;
value: any;
validation: TValidation;
}
export const useValidation = ({
elementName,
value,
validation,
}: IUseValidationArgs) => {
const { validator, errorMessage } = validation || {
validator: undefined,
errorMessage: undefined,
};
const [isValid, setValidation] = useState<boolean | undefined>(undefined);
const { calculationStore } = useStores();
// inject value from store
const validationStatus = calculationStore.validations[elementName];
useEffect(() => {
setValidation(validationStatus);
}, [validationStatus]);
// inner validation && set validation status to store
useEffect(() => {
if (value === undefined || value === '') {
calculationStore.setValidation(elementName, undefined);
} else {
if (validator) {
const validationResult = validator(value);
calculationStore.setValidation(elementName, validationResult);
}
}
}, [value]);
const getValidateStatus = (): ValidateStatus | undefined => {
if (isValid === undefined) {
return undefined;
}
return isValid === false ? 'error' : 'success';
};
const getMessage = (): string | undefined => {
if (isValid === false) {
return errorMessage || INVALID_INPUT_MESSAGE;
}
};
return {
isValid,
validateStatus: getValidateStatus(),
message: getMessage(),
};
};
export const useTableValidation = ({
tableName,
rowIndex,
propName,
value,
validation,
}: IUseTableValidationArgs) => {
const { validator, errorMessage } = validation || {
validator: undefined,
errorMessage: undefined,
};
const [isValid, setValidation] = useState<boolean | undefined>(undefined);
const { calculationStore } = useStores();
const validationStatus =
calculationStore?.tables?.[tableName]?.rows?.[rowIndex]?.[propName]
?.validation;
useEffect(() => {
setValidation(validationStatus);
}, [validationStatus]);
useEffect(() => {
if (value === undefined || value === '') {
calculationStore.setTableRows(
tableName,
rowIndex,
)([
{
[propName]: {
validation: undefined,
},
},
]);
} else {
if (validator) {
const validationResult = validator(value);
calculationStore.setTableRows(
tableName,
rowIndex,
)([
{
[propName]: {
validation: validationResult,
},
},
]);
}
}
}, [value]);
const getValidateStatus = (): ValidateStatus | undefined => {
if (isValid === undefined) {
return undefined;
}
return isValid === false ? 'error' : 'success';
};
const getMessage = (): string | undefined => {
if (isValid === false) {
return errorMessage || INVALID_INPUT_MESSAGE;
}
};
return {
isValid,
validateStatus: getValidateStatus(),
message: getMessage(),
};
};

View File

@ -1,4 +1,4 @@
import { getValueName } from 'client/Containers/Calculation/lib/elements/tools';
import { getValueName } from 'client/Containers/Calculation/Elements/tools';
import initialFilters, {
noResetValueElements
} from 'client/stores/CalculationStore/config/initialFilters';

View File

@ -1,8 +1,8 @@
import elementsTitles, {
tablesTitles,
} from 'client/Containers/Calculation/lib/elements/titles';
tablesTitles
} from 'client/Containers/Calculation/Elements/titles';
import { TableNames } from 'client/Containers/Calculation/types/tables';
import { ICalculationStore } from 'core/types/Calculation/Store';
import { TableNames } from 'core/types/Calculation/Store/tables';
import { omit } from 'lodash';
import { toJS } from 'mobx';

View File

@ -2,8 +2,8 @@ import { message } from 'antd';
import { openNotification } from 'client/Elements/Notification';
import CalculationService from 'core/services/CalculationService';
import { ICalculationStore } from 'core/types/Calculation/Store';
import { resultsValues } from 'core/types/Calculation/Store/values';
import { ElementStatus } from 'core/types/statuses';
import { ValuesNames } from 'core/types/Calculation/Store/values';
import { ElementStatus } from 'types/elements';
import checkValidation from './checkValidation';
import prepareCalculationData from './prepareData';
import results from './results';
@ -11,11 +11,33 @@ import validate from './validate';
const BUTTONS_TIMEOUT = 500;
export const RESULT_VALUES: ValuesNames[] = [
'resultTotalGraphwithNDS',
'resultPlPrice',
'resultPriceUpPr',
'resultIRRGraphPerc',
'resultIRRNominalPerc',
'resultInsKasko',
'resultInsOsago',
'resultDopProdSum',
'resultFirstPayment',
'resultLastPayment',
'resultTerm',
'resultAB_FL',
'resultAB_UL',
'resultBonusMPL',
'resultDopMPLLeasing',
'resultBonusDopProd',
];
export default function (this: ICalculationStore) {
const cleanResults = () => {
for (let resultValue of resultsValues) {
this.setValue(resultValue, '');
}
this.setValues(
RESULT_VALUES.reduce((acc, v) => {
acc[v] = '';
return acc;
}, {}),
);
};
const blockButtons = () => {

View File

@ -1,12 +1,15 @@
import valuesConstants from 'core/constants/values';
import {
PaymentRow,
PreparedValues,
} from 'core/services/CalculationService/types/prepared';
import { PreparedData } from 'core/services/CalculationService/types/request';
import { currentDate } from 'core/tools/date';
import { NIL } from 'core/tools/uuid';
import { PaymentRow, PreparedValues } from 'core/types/Calculation/Prepare';
import { IPreparedData } from 'core/types/Calculation/Requests';
import { ICalculationStore } from 'core/types/Calculation/Store';
import { convertPrice } from '../../lib/tools';
export default function (this: ICalculationStore): IPreparedData {
export default function (this: ICalculationStore): PreparedData {
const { values, options, tables } = this;
const preparedPaymentsRows: PaymentRow[] = Array.from(
@ -97,9 +100,8 @@ export default function (this: ICalculationStore): IPreparedData {
(0.0234 / ((1 - 1 / 1.0234) ^ ((preparedValues.nmper as number) - 2)))
: 1;
preparedValues.loanRate = parseFloat(values.creditRate) / 100;
preparedValues.loanRatePeriod = this.getOption(
'selectRate',
)?.evo_credit_period;
preparedValues.loanRatePeriod =
this.getOption('selectRate')?.evo_credit_period;
preparedValues.balanceHolder = values.balanceHolder;
preparedValues.dogDate = preparedValues.calcDate;
preparedValues.paymentDateNew = undefined;
@ -112,12 +114,10 @@ export default function (this: ICalculationStore): IPreparedData {
(values.lastPaymentRub as number) / (1 + valuesConstants.VAT);
preparedValues.subsidySum =
parseInt(values.subsidySum) / (1 + valuesConstants.VAT);
preparedValues.subsidyPaymentNumber = this.getOption(
'selectSubsidy',
)?.evo_get_subsidy_payment;
preparedValues.fuelCardSum = this.getOption(
'selectFuelCard',
)?.evo_graph_price_withoutnds;
preparedValues.subsidyPaymentNumber =
this.getOption('selectSubsidy')?.evo_get_subsidy_payment;
preparedValues.fuelCardSum =
this.getOption('selectFuelCard')?.evo_graph_price_withoutnds;
preparedValues.scheduleOfPayments = values.graphType;
preparedValues.comissionRub =
(values.comissionRub as number) / (1 + valuesConstants.VAT);

View File

@ -1,18 +1,20 @@
import { Table } from 'client/Containers/Calculation/types/tables';
import valuesConstants from 'core/constants/values';
import { IPreparedData } from 'core/types/Calculation/Requests';
import { IGetCalculationResponse } from 'core/types/Calculation/Responses';
import {
GetCalculationResponse,
PreparedData,
} from 'core/services/CalculationService/types/request';
import { ICalculationStore } from 'core/types/Calculation/Store';
import { ITableCell, TableProps } from 'core/types/Calculation/Store/tables';
export default {
showResultsTable: function (
this: ICalculationStore,
preparedData: IPreparedData,
res: IGetCalculationResponse,
preparedData: PreparedData,
res: GetCalculationResponse,
) {
if (preparedData.preparedValues.nmper) {
const { sumWithVatColumn, vatColumn, sumRepaymentColumn } = res.columns;
const results: TableProps<ITableCell>[] = [];
const results: Table['rows'] = [];
for (let i = 0; i < preparedData.preparedValues.nmper; i++) {
const balanceHolder = this.getValue('balanceHolder');
@ -44,8 +46,8 @@ export default {
},
showResults: function (
this: ICalculationStore,
preparedData: IPreparedData,
res: IGetCalculationResponse,
preparedData: PreparedData,
res: GetCalculationResponse,
) {
const { sumWithVatColumn } = res.columns;
this.setValue(
@ -144,7 +146,7 @@ export default {
},
setResValues: function (
this: ICalculationStore,
res: IGetCalculationResponse,
res: GetCalculationResponse,
) {
this.setValue(
'IRR_Perc',

View File

@ -1,21 +1,18 @@
import { getValueName } from 'client/Containers/Calculation/lib/elements/tools';
import { getValueName } from 'client/Containers/Calculation/Elements/tools';
import { ElementsNames } from 'client/Containers/Calculation/types/elements';
import { pipe } from 'core/tools/func';
import { ICalculationStore } from 'core/types/Calculation/Store';
import {
ElementsNames,
TElements,
} from 'core/types/Calculation/Store/elements';
import CONDITIONS from 'core/validation/conditions';
import {
convertToValidationResult,
getValue,
showValidationMessages,
validate,
ValidationCondition,
ValidationCondition
} from 'core/validation/validate';
import { isNil } from 'lodash';
const customConditions: TElements<ValidationCondition> = {
const customConditions: Partial<Record<ElementsNames, ValidationCondition>> = {
selectLeaseObjectCategory: calculationStore => {
const leaseObjectType = calculationStore.getOption('selectLeaseObjectType');
const leaseObjectCategory = calculationStore.getValue(
@ -82,11 +79,8 @@ const customConditions: TElements<ValidationCondition> = {
return { isValid: true };
},
radioRequirementTelematic: calculationStore => {
const {
telematic,
tracker,
requirementTelematic,
} = calculationStore.getValues([
const { telematic, tracker, requirementTelematic } =
calculationStore.getValues([
'telematic',
'tracker',
'requirementTelematic',
@ -107,10 +101,9 @@ const customConditions: TElements<ValidationCondition> = {
return { isValid: true };
},
selectTownRegistration: calculationStore => {
const {
townRegistration,
objectRegistration,
} = calculationStore.getValues(['townRegistration', 'objectRegistration']);
const { townRegistration, objectRegistration } = calculationStore.getValues(
['townRegistration', 'objectRegistration'],
);
if (objectRegistration === 100000000 && !townRegistration) {
return {
isValid: false,
@ -141,7 +134,9 @@ const customConditions: TElements<ValidationCondition> = {
},
};
const elementsValidations: TElements<any> = {
const elementsValidations: Partial<
Record<ElementsNames, (value?: any) => boolean>
> = {
selectLead: CONDITIONS.IS_NULL,
selectProduct: CONDITIONS.IS_NULL,
selectSupplierCurrency: CONDITIONS.IS_NULL,
@ -163,36 +158,36 @@ const elementsValidations: TElements<any> = {
tbxLeaseObjectCount: CONDITIONS.LESS_OR_EQUALS_ZERO,
};
const elementsConditions = (Object.keys(
elementsValidations,
) as ElementsNames[]).reduce(
(ac: TElements<ValidationCondition>, elementName) => {
ac[elementName] = pipe(
getValue,
elementsValidations[elementName],
convertToValidationResult,
);
return ac;
const elementsConditions = (
Object.keys(elementsValidations) as ElementsNames[]
).reduce(
(ac: Partial<Record<ElementsNames, ValidationCondition>>, elementName) => {
const validator = elementsValidations[elementName];
if (validator)
ac[elementName] = pipe(getValue, validator, convertToValidationResult);
return ac;
},
{},
);
const entityElementsConditions = ([
const entityElementsConditions = (
[
'selectIndAgentRewardCondition',
'selectCalcBrokerRewardCondition',
'selectFinDepartmentRewardCondtion',
] as ElementsNames[]).reduce(
(ac: TElements<ValidationCondition>, elementName) => {
const valueName = getValueName(elementName);
ac[elementName] = (calculationStore, elementName) => {
if (isNil(calculationStore.getValue(valueName))) {
return { isValid: true };
}
return {
isValid: calculationStore.getOption(elementName) !== undefined,
] as ElementsNames[]
).reduce(
(ac: Partial<Record<ElementsNames, ValidationCondition>>, elementName) => {
const valueName = getValueName(elementName);
ac[elementName] = (calculationStore, elementName) => {
if (isNil(calculationStore.getValue(valueName))) {
return { isValid: true };
}
return {
isValid: calculationStore.getOption(elementName) !== undefined,
};
};
};
return ac;
return ac;
},
{},
);

View File

@ -3,12 +3,12 @@ import { AxiosError } from 'axios';
import { openNotification } from 'client/Elements/Notification';
import UserStore from 'client/stores/UserStore';
import { CRM_PROXY_URL } from 'core/constants/urls';
import { getQuotesByLeadQuery } from 'core/graphql/query/crm/quote';
import CrmService from 'core/services/CrmService';
import { quotesByLeadQuery } from 'core/services/CrmService/graphql/query/quote';
import { IQuote } from 'core/services/CrmService/types/entities';
import { ICalculationStore } from 'core/types/Calculation/Store';
import { IQuote } from 'core/types/Entities/crmEntities';
import { toJS } from 'mobx';
import customValues from '../lib/customValues';
import { insKaskoPriceLeasePeriod } from '../computed';
import calculate from './calculate';
async function composeRequest(this: ICalculationStore) {
@ -32,10 +32,9 @@ async function composeRequest(this: ICalculationStore) {
})),
);
const insKaskoPriceLeasePeriod =
customValues.insKaskoPriceLeasePeriod.call(this);
const insKaskoPriceLeasePeriodValue = insKaskoPriceLeasePeriod.call(this);
const calculationValues = Object.assign({}, toJS(this.values), {
insKaskoPriceLeasePeriod,
insKaskoPriceLeasePeriod: insKaskoPriceLeasePeriodValue,
});
const domainname = UserStore.getDomainName();
@ -71,7 +70,7 @@ export default async function (this: ICalculationStore) {
const leadid = this.getValue('lead');
CrmService.getCRMOptions<'quotes', IQuote>({
query: getQuotesByLeadQuery,
query: quotesByLeadQuery,
variables: {
leadid,
},

View File

@ -1,84 +1,9 @@
import { openNotification } from 'client/Elements/Notification';
import { IAutorunEffect } from 'core/types/Calculation/Store/effect';
import { ElementStatus } from 'core/types/statuses';
import { ElementStatus } from 'types/elements';
import { convertPrice } from './lib/tools';
const autorunEffects: IAutorunEffect[] = [
calculationStore => () => {
const { contactClient, contact } = calculationStore.values;
if (contactClient || contact) {
calculationStore.setValidation('selectContactClient', true);
calculationStore.setValidation('tbxContact', true);
}
},
calculationStore => () => {
const { newClient, account } = calculationStore.values;
if (newClient || account) {
calculationStore.setValidation('tbxNewClient', true);
calculationStore.setValidation('selectAccount', true);
}
},
calculationStore => () => {
const { commentLead } = calculationStore.values;
if (commentLead) {
calculationStore.setValidation('tbxCommentLead', true);
}
},
calculationStore => () => {
const { phoneNumber } = calculationStore.values;
if (phoneNumber) {
calculationStore.setValidation('tbxPhoneNumber', true);
}
},
calculationStore => () => {
const { channel } = calculationStore.values;
if (channel) {
calculationStore.setValidation('selectChannel', true);
switch (channel) {
case 100000000: {
const { supplier, agent } = calculationStore.values;
if (supplier) {
calculationStore.setValidation('selectSupplier', true);
}
if (agent) {
calculationStore.setValidation('selectAgent', true);
}
break;
}
case 100000001: {
const { supplier, finDepartment } = calculationStore.values;
if (supplier) {
calculationStore.setValidation('selectSupplier', true);
}
if (finDepartment) {
calculationStore.setValidation('selectFinDepartment', true);
}
break;
}
case 100000002: {
const { agent } = calculationStore.values;
if (agent) {
calculationStore.setValidation('selectAgent', true);
}
break;
}
case 100000003: {
const { broker } = calculationStore.values;
if (broker) {
calculationStore.setValidation('selectBroker', true);
}
break;
}
case 100000004:
default: {
break;
}
}
}
},
// calculationStore => () => {
// const {
// leaseObjectCategory,
@ -131,11 +56,8 @@ const autorunEffects: IAutorunEffect[] = [
ElementStatus.Default,
);
const {
engineVolume,
engineType,
leaseObjectMotorPower,
} = calculationStore.values;
const { engineVolume, engineType, leaseObjectMotorPower } =
calculationStore.values;
if (engineVolume <= 0) {
calculationStore.setValidation('tbxEngineVolume', false);
@ -194,16 +116,13 @@ const autorunEffects: IAutorunEffect[] = [
calculationStore.setValue('subsidySum', subsidy?.evo_subsidy_summ);
} else {
if (subsidy?.evo_max_subsidy_summ) {
const {
leaseObjectPrice,
supplierDiscountRub,
} = calculationStore.values;
const { leaseObjectPrice, supplierDiscountRub } =
calculationStore.values;
const supplierCurrency = calculationStore.getOption(
'selectSupplierCurrency',
);
const evo_currencychanges = calculationStore.getStaticData(
'evo_currencychange',
);
const evo_currencychanges =
calculationStore.getStaticData('evo_currencychange');
const evo_currencychange = evo_currencychanges.find(
x =>
x.evo_ref_transactioncurrency ===

View File

@ -1,6 +1,5 @@
import { ICalculationStore } from 'core/types/Calculation/Store';
import { TValues } from 'core/types/Calculation/Store/values';
import customValues from './lib/customValues';
import { ComputedValuesNames } from 'core/types/Calculation/Store/values';
const LEASE_OBJECT_RISK = {
100000000: 'Низкий',
@ -8,9 +7,32 @@ const LEASE_OBJECT_RISK = {
100000002: 'Высокий',
};
const computedEffects: TValues<
(this: ICalculationStore) => string | number | undefined
> = {
type ComputedEffect = (this: ICalculationStore) => string | number | undefined;
export const insKaskoPriceLeasePeriod: ComputedEffect = function () {
const { leasingPeriod } = this.values;
const { rows } = this.tables.tableInsurance;
const kaskoRow = rows[1];
const dgoRow = rows[2];
const nsRow = rows[3];
let res = 0;
if (
leasingPeriod &&
leasingPeriod > 15 &&
kaskoRow?.insTerm?.value === 100000001
) {
res =
(leasingPeriod / 12) *
(kaskoRow?.insCost?.value +
dgoRow?.insCost?.value +
nsRow?.insCost?.value);
}
return res;
};
const computedEffects: Record<ComputedValuesNames, ComputedEffect> = {
leaseObjectRiskName: function () {
const configuration = this.getOption('selectConfiguration');
if (configuration) {
@ -25,9 +47,7 @@ const computedEffects: TValues<
if (evo_leasingobject_risk)
return LEASE_OBJECT_RISK[evo_leasingobject_risk];
},
insKaskoPriceLeasePeriod: function () {
return customValues.insKaskoPriceLeasePeriod.call(this).toFixed(2);
},
insKaskoPriceLeasePeriod,
irrInfo: function () {
const tarif = this.getOption('selectTarif');
if (tarif && tarif.evo_min_irr && tarif.evo_max_irr) {

View File

@ -1,22 +0,0 @@
export default {
insKaskoPriceLeasePeriod() {
const { leasingPeriod } = this.values;
const { rows } = this.tables.tableInsurance;
const kaskoRow = rows[1];
const dgoRow = rows[2];
const nsRow = rows[3];
let res = 0;
if (
leasingPeriod &&
leasingPeriod > 15 &&
kaskoRow.insTerm.value === 100000001
) {
res =
(leasingPeriod / 12) *
(kaskoRow.insCost.value + dgoRow.insCost.value + nsRow.insCost.value);
}
return res;
},
};

View File

@ -1,15 +1,15 @@
import { message } from 'antd';
import { resetFields as kaskoResetFields } from 'client/Components/Calculation/ELT/Content/Kasko/lib/validation';
import { cancelRequests } from 'client/Components/Calculation/ELT/Content/lib/requests';
import { resetFields as kaskoResetFields } from 'client/Containers/Calculation/Components/ELT/Kasko/lib/validation';
import { cancelRequests } from 'client/Containers/Calculation/Components/ELT/lib/requests';
import {
initIns,
resetIns,
} from 'client/Components/Calculation/ELT/Content/lib/resetIns';
import { resetFields as osagoResetFields } from 'client/Components/Calculation/ELT/Content/Osago/lib/validation';
import { getValueName } from 'client/Containers/Calculation/lib/elements/tools';
resetIns
} from 'client/Containers/Calculation/Components/ELT/lib/resetIns';
import { resetFields as osagoResetFields } from 'client/Containers/Calculation/Components/ELT/Osago/lib/validation';
import { getValueName } from 'client/Containers/Calculation/Elements/tools';
import { ElementsNames } from 'client/Containers/Calculation/types/elements';
import { TCalculationProcess } from 'client/stores/CalculationStore/subStores/calculationProcess';
import { IReactionEffect } from 'core/types/Calculation/Store/effect';
import { ElementsNames } from 'core/types/Calculation/Store/elements';
import { ICalculationStore } from 'core/types/Calculation/Store/index';
import { Process } from 'core/types/Calculation/Store/process';
@ -45,70 +45,72 @@ const eltReactions: IReactionEffect[] = [
},
}),
...resetConf.map(
({ insType, resetFields }) => (
calculationStore: ICalculationStore,
calculationProcess: TCalculationProcess,
) => ({
expression: () => {
return calculationStore.getValues(
(resetFields as ElementsNames[]).map(getValueName),
);
},
effect: () => {
cancelRequests(insType);
({ insType, resetFields }) =>
(
calculationStore: ICalculationStore,
calculationProcess: TCalculationProcess,
) => ({
expression: () => {
return calculationStore.getValues(
(resetFields as ElementsNames[]).map(getValueName),
);
},
effect: () => {
cancelRequests(insType);
if (
calculationProcess.hasProcess(Process.Init) ||
calculationProcess.hasProcess(Process.ELT) ||
calculationProcess.hasProcess(Process.LoadKp)
) {
return;
}
if (
calculationProcess.hasProcess(Process.Init) ||
calculationProcess.hasProcess(Process.ELT) ||
calculationProcess.hasProcess(Process.LoadKp)
) {
return;
}
const { ELTStore } = calculationStore.stores;
if (ELTStore[insType]?.isReseted()) {
return;
}
message.warn({ content: RESET_MESSAGES[insType] });
resetIns.call(calculationStore, insType);
},
}),
const { ELTStore } = calculationStore.stores;
if (ELTStore[insType]?.isReseted()) {
return;
}
message.warn({ content: RESET_MESSAGES[insType] });
resetIns.call(calculationStore, insType);
},
}),
),
...resetConf.map(
({ insType, tableRowNumber }) => (
calculationStore: ICalculationStore,
calculationProcess: TCalculationProcess,
) => ({
expression: () => {
return [
...['insuranceCompany', 'insCost'].map(
fieldName =>
calculationStore.tables.tableInsurance.rows[tableRowNumber][
fieldName
].value,
),
];
},
effect: () => {
cancelRequests(insType);
({ insType, tableRowNumber }) =>
(
calculationStore: ICalculationStore,
calculationProcess: TCalculationProcess,
) => ({
expression: () => {
return [
...['insuranceCompany', 'insCost'].map(
fieldName =>
calculationStore.tables.tableInsurance.rows[tableRowNumber][
fieldName
].value,
),
];
},
effect: () => {
cancelRequests(insType);
if (
calculationProcess.hasProcess(Process.Init) ||
calculationProcess.hasProcess(Process.ELT) ||
calculationProcess.hasProcess(Process.LoadKp)
) {
return;
}
if (
calculationProcess.hasProcess(Process.Init) ||
calculationProcess.hasProcess(Process.ELT) ||
calculationProcess.hasProcess(Process.LoadKp)
) {
return;
}
const { ELTStore } = calculationStore.stores;
if (ELTStore[insType]?.isReseted()) {
return;
}
message.warn({ content: RESET_MESSAGES[insType] });
resetIns.call(calculationStore, insType);
},
}),
const { ELTStore } = calculationStore.stores;
if (ELTStore[insType]?.isReseted()) {
return;
}
message.warn({ content: RESET_MESSAGES[insType] });
resetIns.call(calculationStore, insType);
},
}),
),
];

View File

@ -1,20 +1,18 @@
import { gql } from '@apollo/client';
import { getValueName } from 'client/Containers/Calculation/lib/elements/tools';
import { getValueName } from 'client/Containers/Calculation/Elements/tools';
import { ElementsNames } from 'client/Containers/Calculation/types/elements';
import { openNotification } from 'client/Elements/Notification';
import _1CService from 'core/services/1CService';
import CrmService from 'core/services/CrmService';
import { IEvoTown } from 'core/services/CrmService/types/entities';
import { currentDate } from 'core/tools/date';
import { IReactionEffect } from 'core/types/Calculation/Store/effect';
import {
ElementsNames,
TElements,
} from 'core/types/Calculation/Store/elements';
import { Process } from 'core/types/Calculation/Store/process';
import { IEvoTown } from 'core/types/Entities/crmEntities';
import { ElementStatus } from 'core/types/statuses';
import { get } from 'lodash';
import { ElementStatus } from 'types/elements';
const v: TElements<any> = {
//TODO: beautify
const v = {
tbxVehicleTaxInYear: { value: 0, validator: value => value === 0 },
radioTypePTS: { value: null, validator: value => value === null },
// selectObjectRegionRegistration: {

View File

@ -1,5 +1,5 @@
import { ElementsNames } from 'client/Containers/Calculation/types/elements';
import { IReactionEffect } from 'core/types/Calculation/Store/effect';
import { ElementsNames } from 'core/types/Calculation/Store/elements';
import { LinksNames } from 'core/types/Calculation/Store/links';
export default ([

View File

@ -1,104 +1,107 @@
import { IQuote } from 'core/services/CrmService/types/entities';
import { ValuesNames } from 'core/types/Calculation/Store/values';
import { IQuote } from 'core/types/Entities/crmEntities';
const mapKPtoValues: Partial<Record<ValuesNames, keyof IQuote | string>> = {
product: 'evo_baseproductid',
clientType: 'evo_client_typeid',
leaseObjectPrice: 'evo_supplier_currency_price',
supplierCurrency: 'evo_transactioncurrencyid',
supplierDiscountRub: 'evo_discount_supplier_currency',
supplierDiscountPerc: 'evo_discount_perc',
firstPaymentPerc: 'evo_first_payment_perc',
lastPaymentRule: 'evo_last_payment_calc',
lastPaymentPerc: 'evo_last_payment_perc',
lastPaymentRub: 'evo_last_payment_rub',
// balanceHolder: 'evo_balance_holder',
graphType: 'evo_graph_type',
parmentsDecreasePercent: 'evo_payments_decrease_perc',
seasonType: 'evo_seasons_type',
highSeasonStart: 'evo_high_season',
comissionPerc: 'evo_comission_perc',
comissionRub: 'evo_comission_rub',
saleBonus: 'evo_sale_bonus',
leasingPeriod: 'evo_period',
tarif: 'evo_tarifid',
// creditRate: 'evo_rate',
IRR_Perc: 'evo_msfo_irr',
leaseObjectType: 'evo_leasingobject_typeid',
deliveryTime: 'evo_delivery_time',
brand: 'evo_brandid',
model: 'evo_modelid',
configuration: 'evo_equipmentid',
leaseObjectYear: 'evo_year',
engineType: 'evo_engine_type',
leaseObjectCategory: 'evo_category',
leaseObjectMotorPower: 'evo_power',
engineVolume: 'evo_engine_volume',
leaseObjectUseFor: 'evo_use_for',
withTrailer: 'evo_trailer',
leaseObjectUsed: 'evo_leasingobject_used',
maxMass: 'evo_max_mass',
countSeats: 'evo_seats',
maxSpeed: 'evo_max_speed',
dealer: 'evo_supplier_accountid',
dealerPerson: 'evo_dealer_person_accountid',
dealerRewardCondition: 'evo_dealer_reward_conditionid',
dealerRewardSumm: 'evo_dealer_reward_total',
dealerBroker: 'evo_dealer_broker_accountid',
dealerBrokerRewardCondition: 'evo_dealer_broker_reward_conditionid',
dealerBrokerRewardSumm: 'evo_dealer_broker_reward_total',
// indAgent: 'evo_agent_accountid',
// indAgentRewardCondition: 'evo_agent_reward_conditionid',
// indAgentRewardSumm: 'evo_agent_reward_total',
calcDoubleAgent: 'evo_double_agent_accountid',
calcDoubleAgentRewardCondition: 'evo_double_agent_reward_conditionid',
calcDoubleAgentRewardSumm: 'evo_double_agent_reward_total',
// calcBroker: 'evo_broker_accountid',
// calcBrokerRewardCondition: 'evo_broker_reward_conditionid',
// calcBrokerRewardSum: 'evo_broker_reward_total',
// calcFinDepartment: 'evo_fin_department_accountid',
// finDepartmentRewardCondtion: 'evo_fin_department_reward_conditionid',
// finDepartmentRewardSumm: 'evo_fin_department_reward_total',
GPSBrand: 'evo_gps_brandid',
GPSModel: 'evo_gps_modelid',
infuranceOPF: 'evo_ins_legal_form',
insKaskoType: 'evo_insurance_type',
insKaskoPriceLeasePeriod: 'evo_kasko_price_leasperiod',
insDecentral: 'evo_insurance_decentral',
insPeriod: 'evo_insurance_period',
insFranchise: 'evo_franchise',
insUnlimitDrivers: 'evo_unlimit_drivers',
insAgeDrivers: 'evo_age_drivers',
insExpDrivers: 'evo_exp_drivers',
lastPaymentRedemption: 'evo_last_payment_redemption',
priceWithDiscount: 'evo_price_with_discount',
costIncrease: 'evo_cost_increace',
insurance: 'evo_insurance',
registrationQuote: 'evo_registration_quote',
technicalCardQuote: 'evo_card_quote',
NSIB: 'evo_nsib_quote',
quoteName: 'evo_contact_name',
quoteContactGender: 'evo_gender',
quoteRedemptionGraph: 'evo_redemption_graph',
minPriceChange: 'evo_min_change_price',
maxPriceChange: 'evo_max_price_change',
importerRewardPerc: 'evo_importer_reward_perc',
importerRewardRub: 'evo_importer_reward_rub',
// requirementTelematic: 'evo_req_telematic_accept',
mileage: 'evo_mileage',
fullPriceWithDiscount: 'evo_price_without_discount_quote',
objectRegistration: 'evo_object_registration',
objectRegionRegistration: 'evo_registration_regionid',
// vehicleTaxInYear: 'evo_vehicle_tax_approved',
objectCategoryTax: 'evo_category_tr',
objectTypeTax: 'evo_vehicle_type_tax',
typePTS: 'evo_pts_type',
subsidy: 'evo_subsidyid',
subsidySum: 'evo_subsidy_summ',
const mapKPtoValues: Partial<Record<keyof IQuote | string, ValuesNames>> = {
evo_baseproductid: 'product',
evo_client_typeid: 'clientType',
evo_supplier_currency_price: 'leaseObjectPrice',
evo_transactioncurrencyid: 'supplierCurrency',
evo_discount_supplier_currency: 'supplierDiscountRub',
evo_discount_perc: 'supplierDiscountPerc',
evo_first_payment_perc: 'firstPaymentPerc',
evo_last_payment_calc: 'lastPaymentRule',
evo_last_payment_perc: 'lastPaymentPerc',
evo_last_payment_rub: 'lastPaymentRub',
// evo_balance_holder: 'balanceHolder',
evo_graph_type: 'graphType',
evo_payments_decrease_perc: 'parmentsDecreasePercent',
evo_seasons_type: 'seasonType',
evo_high_season: 'highSeasonStart',
evo_comission_perc: 'comissionPerc',
evo_comission_rub: 'comissionRub',
evo_sale_bonus: 'saleBonus',
evo_period: 'leasingPeriod',
evo_tarifid: 'tarif',
// evo_rate: 'creditRate',
evo_msfo_irr: 'IRR_Perc',
evo_leasingobject_typeid: 'leaseObjectType',
evo_delivery_time: 'deliveryTime',
evo_brandid: 'brand',
evo_modelid: 'model',
evo_equipmentid: 'configuration',
evo_year: 'leaseObjectYear',
evo_engine_type: 'engineType',
evo_category: 'leaseObjectCategory',
evo_power: 'leaseObjectMotorPower',
evo_engine_volume: 'engineVolume',
evo_use_for: 'leaseObjectUseFor',
evo_trailer: 'withTrailer',
evo_leasingobject_used: 'leaseObjectUsed',
evo_max_mass: 'maxMass',
evo_seats: 'countSeats',
evo_max_speed: 'maxSpeed',
evo_supplier_accountid: 'dealer',
evo_dealer_person_accountid: 'dealerPerson',
evo_dealer_reward_conditionid: 'dealerRewardCondition',
evo_dealer_reward_total: 'dealerRewardSumm',
evo_dealer_broker_accountid: 'dealerBroker',
evo_dealer_broker_reward_conditionid: 'dealerBrokerRewardCondition',
evo_dealer_broker_reward_total: 'dealerBrokerRewardSumm',
// evo_agent_accountid: indAgent,
// evo_agent_reward_conditionid: 'indAgentRewardCondition',
// evo_agent_reward_total: indAgentRewardSumm,
evo_double_agent_accountid: 'calcDoubleAgent',
evo_double_agent_reward_conditionid: 'calcDoubleAgentRewardCondition',
evo_double_agent_reward_total: 'calcDoubleAgentRewardSumm',
// evo_broker_accountid: 'calcBroker',
// evo_broker_reward_conditionid: 'calcBrokerRewardCondition',
// evo_broker_reward_total: 'calcBrokerRewardSum',
// evo_fin_department_accountid: 'calcFinDepartment',
// evo_fin_department_reward_conditionid: 'finDepartmentRewardCondtion',
// evo_fin_department_reward_total: 'finDepartmentRewardSumm'
evo_gps_brandid: 'GPSBrand',
evo_gps_modelid: 'GPSModel',
evo_ins_legal_form: 'infuranceOPF',
evo_insurance_type: 'insKaskoType',
evo_insurance_decentral: 'insDecentral',
evo_franchise: 'insFranchise',
evo_unlimit_drivers: 'insUnlimitDrivers',
evo_age_drivers: 'insAgeDrivers',
evo_exp_drivers: 'insExpDrivers',
evo_last_payment_redemption: 'lastPaymentRedemption',
evo_price_with_discount: 'priceWithDiscount',
evo_cost_increace: 'costIncrease',
evo_insurance: 'insurance',
evo_registration_quote: 'registrationQuote',
evo_card_quote: 'technicalCardQuote',
evo_nsib_quote: 'NSIB',
evo_contact_name: 'quoteName',
evo_gender: 'quoteContactGender',
evo_redemption_graph: 'quoteRedemptionGraph',
evo_min_change_price: 'minPriceChange',
evo_max_price_change: 'maxPriceChange',
evo_importer_reward_perc: 'importerRewardPerc',
evo_importer_reward_rub: 'importerRewardRub',
// evo_req_telematic_accept: 'requirementTelematic',
evo_mileage: 'mileage',
evo_price_without_discount_quote: 'fullPriceWithDiscount',
evo_object_registration: 'objectRegistration',
evo_registration_regionid: 'objectRegionRegistration',
// evo_vehicle_tax_approved: vehicleTaxInYear,
evo_category_tr: 'objectCategoryTax',
evo_vehicle_type_tax: 'objectTypeTax',
evo_pts_type: 'typePTS',
evo_subsidyid: 'subsidy',
evo_subsidy_summ: 'subsidySum',
};
export const getKpPropName = (
valueName: ValuesNames,
): keyof IQuote | string | undefined => mapKPtoValues[valueName];
export default mapKPtoValues;
export function getValuesFromKP(quote: IQuote) {
return Object.keys(mapKPtoValues).reduce((acc, kpProp) => {
const valueName = mapKPtoValues[kpProp];
if (valueName) {
const value = quote[kpProp];
acc[valueName] = value;
}
return acc;
}, {} as Partial<Record<ValuesNames, any>>);
}

View File

@ -3,24 +3,10 @@ import valuesConstants from 'core/constants/values';
import { pipe } from 'core/tools/func';
import { IReactionEffect } from 'core/types/Calculation/Store/effect';
import { Process } from 'core/types/Calculation/Store/process';
import { ElementStatus } from 'core/types/statuses';
import { get, intersection, round } from 'lodash';
import { ElementStatus } from 'types/elements';
const reactionEffects: IReactionEffect[] = [
// calculationStore => ({
// expression: () => {
// const { options } = calculationStore;
// return options.selectQuote;
// },
// effect: quotes => {
// if (quotes.length > 0) {
// calculationStore.setStatus('tbxQuoteName', Status.Disabled);
// } else {
// calculationStore.setStatus('tbxQuoteName', Status.Default);
// }
// },
// }),
calculationStore => ({
expression: () => {
const { opportunity } = calculationStore.values;
@ -37,131 +23,6 @@ const reactionEffects: IReactionEffect[] = [
},
}),
calculationStore => ({
expression: () => {
const { agent } = calculationStore.values;
return agent;
},
effect: agentid => {
if (!agentid) {
calculationStore.setStatus('selectDoubleAgent', ElementStatus.Disabled);
} else {
calculationStore.setStatus('selectDoubleAgent', ElementStatus.Default);
}
},
}),
calculationStore => ({
expression: () => {
const { channel } = calculationStore.values;
return channel;
},
effect: channel => {
switch (channel) {
case 100000000:
calculationStore.setStatus('selectSupplier', ElementStatus.Default);
calculationStore.setStatus('selectAgent', ElementStatus.Default);
calculationStore.setStatus(
'selectFinDepartment',
ElementStatus.Disabled,
);
calculationStore.setValue('finDepartment', null);
calculationStore.setStatus('selectBroker', ElementStatus.Disabled);
calculationStore.setValue('broker', null);
break;
case 100000001:
calculationStore.setStatus('selectSupplier', ElementStatus.Default);
calculationStore.setStatus('selectAgent', ElementStatus.Default);
calculationStore.setStatus(
'selectFinDepartment',
ElementStatus.Default,
);
calculationStore.setStatus('selectBroker', ElementStatus.Disabled);
calculationStore.setValue('broker', null);
break;
case 100000002:
calculationStore.setStatus('selectSupplier', ElementStatus.Disabled);
calculationStore.setValue('supplier', null);
calculationStore.setStatus('selectAgent', ElementStatus.Default);
calculationStore.setStatus(
'selectFinDepartment',
ElementStatus.Disabled,
);
calculationStore.setValue('finDepartment', null);
calculationStore.setStatus('selectBroker', ElementStatus.Disabled);
calculationStore.setValue('broker', null);
break;
case 100000003:
calculationStore.setStatus('selectSupplier', ElementStatus.Disabled);
calculationStore.setValue('supplier', null);
calculationStore.setStatus('selectAgent', ElementStatus.Default);
calculationStore.setValue('agent', null);
calculationStore.setStatus(
'selectFinDepartment',
ElementStatus.Disabled,
);
calculationStore.setValue('finDepartment', null);
calculationStore.setStatus('selectBroker', ElementStatus.Default);
break;
case 100000004:
default:
calculationStore.setStatus('selectSupplier', ElementStatus.Disabled);
calculationStore.setValue('supplier', null);
calculationStore.setStatus('selectAgent', ElementStatus.Disabled);
calculationStore.setValue('agent', null);
calculationStore.setStatus(
'selectFinDepartment',
ElementStatus.Disabled,
);
calculationStore.setValue('finDepartment', null);
calculationStore.setStatus('selectBroker', ElementStatus.Disabled);
calculationStore.setValue('broker', null);
break;
}
},
options: {
fireImmediately: true,
},
}),
calculationStore => ({
expression: () => {
const { newClient } = calculationStore.values;
return newClient;
},
effect: newClient => {
if (newClient && newClient.length > 0) {
calculationStore.setValue('account', null);
calculationStore.setValue('contactClient', null);
calculationStore.setStatus('selectAccount', ElementStatus.Disabled);
calculationStore.setStatus(
'selectContactClient',
ElementStatus.Disabled,
);
} else {
calculationStore.setStatus('selectAccount', ElementStatus.Default);
calculationStore.setStatus(
'selectContactClient',
ElementStatus.Default,
);
}
},
}),
(calculationStore, calculationProcess) => ({
expression: () => {
const { indAgentRewardCondition } = calculationStore.values;
@ -578,50 +439,6 @@ const reactionEffects: IReactionEffect[] = [
},
}),
calculationStore => ({
expression: () => {
const { insUnlimitDrivers } = calculationStore.values;
return insUnlimitDrivers;
},
effect: insUnlimitDrivers => {
if (insUnlimitDrivers) {
calculationStore.setStatus('tbxInsAgeDrivers', ElementStatus.Disabled);
calculationStore.setStatus('tbxInsExpDrivers', ElementStatus.Disabled);
calculationStore.setStatus(
'btnDriversApplication',
ElementStatus.Disabled,
);
} else {
calculationStore.setStatus('tbxInsAgeDrivers', ElementStatus.Default);
calculationStore.setStatus('tbxInsExpDrivers', ElementStatus.Default);
calculationStore.setStatus(
'btnDriversApplication',
ElementStatus.Default,
);
}
},
options: {
fireImmediately: true,
},
}),
calculationStore => ({
expression: () => {
const { insFranchise } = calculationStore.values;
return insFranchise;
},
effect: insFranchise => {
if (!insFranchise || parseInt(insFranchise) === 0) {
calculationStore.setStatus('btnFranschise', ElementStatus.Disabled);
} else {
calculationStore.setStatus('btnFranschise', ElementStatus.Default);
}
},
options: {
fireImmediately: true,
},
}),
calculationStore => ({
expression: () => {
const { lastPaymentRule } = calculationStore.values;

View File

@ -1,13 +1,13 @@
import { getFieldName } from 'client/Containers/Calculation/lib/elements/tools';
import { getFieldName } from 'client/Containers/Calculation/Elements/tools';
import { InteractionElementsNames } from 'client/Containers/Calculation/types/elements';
import { TableNames } from 'client/Containers/Calculation/types/tables';
import { openNotification } from 'client/Elements/Notification';
import valuesConstants from 'core/constants/values';
import { pipe } from 'core/tools/func';
import { IReactionEffect } from 'core/types/Calculation/Store/effect';
import { ElementsNames } from 'core/types/Calculation/Store/elements';
import { Process } from 'core/types/Calculation/Store/process';
import { TableNames } from 'core/types/Calculation/Store/tables';
import { ValuesNames } from 'core/types/Calculation/Store/values';
import { ElementStatus } from 'core/types/statuses';
import { ElementStatus } from 'types/elements';
import { convertPrice } from '../lib/tools';
import { getPrice } from './priceReactions/calculate';
@ -265,11 +265,8 @@ const reactionEffects: IReactionEffect[] = [
calculationStore => ({
expression: () => {
const {
countSeats,
leaseObjectCategory,
recalcWithRevision,
} = calculationStore.values;
const { countSeats, leaseObjectCategory, recalcWithRevision } =
calculationStore.values;
return {
countSeats,
leaseObjectCategory,
@ -579,7 +576,7 @@ const map_add_product_types_to_values = {
telematics: 100000004,
};
const elementsToDisable: (ElementsNames | TableNames)[] = [
const elementsToDisable: (InteractionElementsNames | TableNames)[] = [
'tablePayments',
'selectLead',
'selectOpportunity',
@ -605,7 +602,6 @@ const elementsToDisable: (ElementsNames | TableNames)[] = [
'selectIndAgent',
'selectCalcBroker',
'selectCalcFinDepartment',
'tbxInsKaskoPriceLeasePeriod',
'selectTarif',
'tbxCreditRate',
'selectRate',
@ -620,7 +616,7 @@ const elementsToDisable: (ElementsNames | TableNames)[] = [
];
// Для recalc = true и первого платежа = 0
const agentsElementsToDisable: ElementsNames[] = [
const agentsElementsToDisable: InteractionElementsNames[] = [
'selectDealerRewardCondition',
'tbxDealerRewardSumm',
'selectDealerBroker',

View File

@ -1,9 +1,6 @@
import { gql } from '@apollo/client';
import { getQuotesByLeadQuery } from 'core/graphql/query/crm/quote';
import CrmService from 'core/services/CrmService';
import { currentISODate } from 'core/tools/date';
import { IReactionEffect } from 'core/types/Calculation/Store/effect';
import { Process } from 'core/types/Calculation/Store/process';
import { quotesByLeadQuery } from 'core/services/CrmService/graphql/query/quote';
import {
IAccount,
IEvoEquipment,
@ -13,8 +10,11 @@ import {
IEvoTown,
IQuote,
ISalonProvider,
} from 'core/types/Entities/crmEntities';
import { ElementStatus } from 'core/types/statuses';
} from 'core/services/CrmService/types/entities';
import { currentISODate } from 'core/tools/date';
import { IReactionEffect } from 'core/types/Calculation/Store/effect';
import { Process } from 'core/types/Calculation/Store/process';
import { ElementStatus } from 'types/elements';
export default [
(calculationStore, calculationProcess) => ({
@ -51,7 +51,7 @@ export default [
if (lead?.leadid) {
CrmService.getCRMOptions<'quotes', IQuote>({
query: getQuotesByLeadQuery,
query: quotesByLeadQuery,
variables: {
leadid: lead?.leadid,
},
@ -259,24 +259,6 @@ export default [
},
}),
(calculationStore, calculationProcess) => ({
expression: () => {
const { account } = calculationStore.values;
return account;
},
effect: account => {
if (calculationProcess.hasProcess(Process.LoadKp)) {
return;
}
if (account && account.length > 0) {
calculationStore.setStatus('tbxNewClient', ElementStatus.Disabled);
calculationStore.setValue('newClient', null);
} else {
calculationStore.setStatus('tbxNewClient', ElementStatus.Default);
}
},
}),
(calculationStore, calculationProcess) => ({
expression: () => {
const { indAgent } = calculationStore.values;
@ -899,113 +881,6 @@ export default [
},
}),
(calculationStore, calculationProcess) => ({
expression: () => {
const { supplier } = calculationStore.values;
return supplier;
},
effect: supplierId => {
if (calculationProcess.hasProcess(Process.LoadKp)) {
return;
}
calculationStore.setOptions('selectFinDepartment', []);
calculationStore.setValue('finDepartment', null);
if (supplierId) {
const supplier = calculationStore.getOption('selectSupplier', {
accountid: supplierId,
});
if (supplier && supplier.evo_fin_department_accountid)
CrmService.getCRMOptions<'accountOptions', IAccount>({
query: gql`
query selectFinDepartment($accountid: Uuid!) {
accountOptions: account(accountid: $accountid) {
accountid
name
}
}
`,
variables: {
accountid: supplier.evo_fin_department_accountid,
},
}).then(({ accountOptions }) => {
if (accountOptions) {
calculationStore.setOptions(
'selectFinDepartment',
accountOptions,
);
}
});
}
},
}),
(calculationStore, calculationProcess) => ({
expression: () => {
const { supplier, channel } = calculationStore.values;
return { supplierId: supplier, channelId: channel };
},
//TODO: add $ownerid: Uuid
effect: ({ supplierId, channelId }) => {
if (calculationProcess.hasProcess(Process.LoadKp)) {
return;
}
calculationStore.setOptions('selectAgent', []);
calculationStore.setValue('agent', null);
if (channelId === 100000002) {
CrmService.getCRMOptions<'accountOptions', IAccount>({
query: gql`
query selectAgent_1(
$statecode: Int
$evo_account_type: [Int!]
$evo_legal_form: Int
) {
accountOptions: accounts(
statecode: $statecode
evo_account_type: $evo_account_type
evo_legal_form: $evo_legal_form
) {
accountid
name
}
}
`,
variables: {
statecode: 0,
evo_account_type: [100000005],
evo_legal_form: 100000004,
},
}).then(({ accountOptions }) => {
if (accountOptions) {
calculationStore.setOptions('selectAgent', accountOptions);
}
});
} else {
if (supplierId) {
CrmService.getCRMOptions<'accountOptions', IAccount>({
query: gql`
query selectAgent_2($statecode: Int, $salonaccountid: Uuid!) {
account: salon_agents(
statecode: $statecode
salonaccountid: $salonaccountid
) {
accountid
name
}
}
`,
variables: {
statecode: 0,
salonaccountid: supplierId,
},
}).then(({ accountOptions }) => {
if (accountOptions) {
calculationStore.setOptions('selectAgent', accountOptions);
}
});
}
}
},
}),
(calculationStore, calculationProcess) => ({
expression: () => {
const { GPSBrand } = calculationStore.values;

View File

@ -1,6 +1,6 @@
import { ElementsNames } from 'client/Containers/Calculation/types/elements';
import { IReactionEffect } from 'core/types/Calculation/Store/effect';
import { ElementsNames } from 'core/types/Calculation/Store/elements';
import { ElementStatus } from 'core/types/statuses';
import { ElementStatus } from 'types/elements';
const elementsNames: ElementsNames[] = [
'selectModel',

View File

@ -1,4 +1,4 @@
/* eslint-disable @typescript-eslint/ban-ts-comment */
import { Table } from 'client/Containers/Calculation/types/tables';
import { openNotification } from 'client/Elements/Notification';
import {
insuranceKaskoDefaultFilter,
@ -9,9 +9,9 @@ import valuesConstants from 'core/constants/values';
import { shift, shiftRight } from 'core/tools/array';
import { IReactionEffect } from 'core/types/Calculation/Store/effect';
import { Process } from 'core/types/Calculation/Store/process';
import { ITableCell, TableProps } from 'core/types/Calculation/Store/tables';
import { ElementStatus } from 'core/types/statuses';
import { toJS } from 'mobx';
import { ElementStatus } from 'types/elements';
const { PERIODS_NUMBER } = valuesConstants;
export default [
@ -122,9 +122,8 @@ export default [
},
effect: ({ insTerm, leasingPeriod }) => {
const quote = calculationStore.getOption('selectQuote');
const recalcWithRevision = calculationStore.getValue(
'recalcWithRevision',
);
const recalcWithRevision =
calculationStore.getValue('recalcWithRevision');
if (
recalcWithRevision &&
quote?.evo_one_year_insurance &&
@ -406,12 +405,8 @@ export default [
(calculationStore, calculationProcess) => ({
expression: () => {
const {
leasingPeriod,
graphType,
parmentsDecreasePercent,
seasonType,
} = calculationStore.values;
const { leasingPeriod, graphType, parmentsDecreasePercent, seasonType } =
calculationStore.values;
const highSeasonStart = calculationStore.getOption(
'selectHighSeasonStart',
@ -442,7 +437,7 @@ export default [
const prevValues = toJS(calculationStore.tables.tablePayments.rows).map(
x => x.paymentRelation?.value,
);
let payments: TableProps<ITableCell>[] = [
let payments: Table['rows'] = [
{
paymentRelation: {
value: firstPaymentPerc,
@ -753,7 +748,8 @@ export default [
const prevIsTrailer = prevLeaseObjectCategory === 100000004;
if (nextIsTrailer) {
const otherInsuranceCompany = calculationStore.tables.tableInsurance.options?.insuranceCompany?.find(
const otherInsuranceCompany =
calculationStore.tables.tableInsurance.options?.insuranceCompany?.find(
x => x.name?.includes('ПРОЧИЕ'),
);
if (otherInsuranceCompany) {

View File

@ -1,4 +1,4 @@
import { initIns } from 'client/Components/Calculation/ELT/Content/lib/resetIns';
import { initIns } from 'client/Containers/Calculation/Components/ELT/lib/resetIns';
import { IWhenEffect } from 'core/types/Calculation/Store/effect';
const whenEffects: IWhenEffect[] = [

View File

@ -1,10 +1,7 @@
import {
ElementsNames,
TElements,
} from 'core/types/Calculation/Store/elements';
import { ElementsNames } from 'client/Containers/Calculation/types/elements';
import { TElementFilter } from 'core/types/Calculation/Store/filters';
const initialFilters: TElements<TElementFilter> = {};
const initialFilters: Partial<Record<ElementsNames, TElementFilter>> = {};
export const noResetValueElements: ElementsNames[] = ['selectTechnicalCard'];

View File

@ -1,42 +1,8 @@
import { ElementsNames } from 'client/Containers/Calculation/types/elements';
import { IBaseOption } from 'core/services/CrmService/types/common';
import { TElements } from 'core/types/Calculation/Store/elements';
import { orderBy } from 'lodash';
const initialOptions: TElements<IBaseOption[]> = {
selectChannel: [
{
name: 'От агента-ФЛ-сотрудника поставщика',
value: 100000000,
},
{
name: 'Поставщик (финотдел)',
value: 100000001,
},
{
name: 'От агента-ФЛ (не сотрудник поставщика)',
value: 100000002,
},
{
name: 'Брокер (ЮЛ/ИП не связан с поставщиком)',
value: 100000003,
},
{
name: 'Прочее',
value: 100000004,
},
],
radioContactGender: [
{
name: 'Мужской',
value: 100000000,
},
{
name: 'Женский',
value: 100000001,
},
],
const initialOptions: Partial<Record<ElementsNames, IBaseOption[]>> = {
radioLastPaymentRule: [
{
name: 'рублей',

Some files were not shown because too many files have changed in this diff Show More