import { useEffect, useState } from "react"; import { enqueueSnackbar } from "notistack"; import type { TagKeys, SelectedTags, QuestionKeys, SelectedQuestions, MinifiedData } from "./types"; import { AccountResponse, getIntegrationRules, getPipelines, getSteps, getTags, getUsers, getAccount, FieldsRule, getFields, connectBitrix, } from "@/api/bitrixIntegration"; import { AnyTypedQuizQuestion } from "@frontend/squzanswerer"; import { UntypedQuizQuestion } from "@/model/questionTypes/shared"; const SIZE = 25; interface Props { isModalOpen: boolean; isTryRemoveAccount: boolean; quizID: number; questions: (AnyTypedQuizQuestion | UntypedQuizQuestion)[] } const FCTranslate = { "name": "имя", "email": "почта", "phone": "телефон", "text": "номер", "address": "адрес", } let isReadyGetPipeline = true; let isReadyGetPipelineStep = true; let isReadyGetUsers = true; let isReadyGetTags = true; let isReadyGetFields = true; export const useBitrixIntegration = ({ isModalOpen, isTryRemoveAccount, quizID, questions }: Props) => { const [isLoadingPage, setIsLoadingPage] = useState(true); const [firstRules, setFirstRules] = useState(false); const [accountInfo, setAccountInfo] = useState(null); const [leadFlag, setLeadFlag] = useState(false); const [arrayOfPipelines, setArrayOfPipelines] = useState([]); const [arrayOfPipelinesSteps, setArrayOfPipelinesSteps] = useState([]); const [fullArrayOfPipelinesSteps, setFullArrayOfPipelinesSteps] = useState([]); const [arrayOfUsers, setArrayOfUsers] = useState([]); const [arrayOfTags, setArrayOfTags] = useState([]); const [arrayOfFields, setArrayOfFields] = useState([]); const [selectedPipeline, setSelectedPipeline] = useState(null); const [selectedPipelineStep, setSelectedPipelineStep] = useState(null); const [selectedDealUser, setSelectedDealPerformer] = useState(null); const [selectedCurrentFields, setSelectedCurrentFields] = useState([]); const [questionsBackend, setQuestionsBackend] = useState({} as FieldsRule); const [selectedTags, setSelectedTags] = useState({ Lead: [], Contact: [], Company: [], Customer: [], }); const [selectedQuestions, setSelectedQuestions] = useState({ lead: [], company: [], contact: [], deal: [], CRM_INVOICE: [], CRM_SMART_INVOICE: [], CRM_QUOTE: [], CRM_REQUISITE: [], }); const [pageOfPipelines, setPageOfPipelines] = useState(1); const [pageOfPipelinesSteps, setPageOfPipelinesSteps] = useState(1); const [pageOfUsers, setPageOfUsers] = useState(1); const [pageOfTags, setPageOfTags] = useState(1); const [pageOfFields, setPageOfFields] = useState(1); const leadFlagHC = (s:boolean) => { setLeadFlag(s) }; const selectedPipelineHC = (id:string | null) => { setSelectedPipeline(id); isReadyGetPipelineStep = true; setPageOfPipelinesSteps(1); } // useEffect(() => { // (async () => { // const API_URL = `https://penadigitaltech.bitrix24.ru`; // try { // const response = await makeRequest({ // method: "POST", // url: `${API_URL}/account`, // useToken: true, // withCredentials: true, // body: { // "client_bitrix_url": "penadigitaltech.bitrix24.ru" // } // }); // window.open(response.link, "_blank"); // } catch (nativeError) { // return [null, `Не удалось подключить аккаунт. `]; // } // })() // }, [isModalOpen]) useEffect(() => { const fetchAccountRules = async () => { setIsLoadingPage(true); const [account, accountError] = await getAccount(); if (accountError) { if (!accountError.includes("Not Found")) enqueueSnackbar(accountError); setAccountInfo(null); } if (account) { setAccountInfo(account); } const [settingsResponse, rulesError] = await getIntegrationRules(quizID.toString()); if (rulesError) { if (rulesError === "first") setFirstRules(true); if (!rulesError.includes("Not Found") && !rulesError.includes("first")) enqueueSnackbar(rulesError); } if (settingsResponse) { if (settingsResponse.PipelineID) selectedPipelineHC(settingsResponse.PipelineID.toString()); if (settingsResponse.StepID) setSelectedPipelineStep(settingsResponse.StepID.toString()); if (settingsResponse.PerformerID) setSelectedDealPerformer(settingsResponse.PerformerID.toString()); console.log("settingsResponse") console.log(settingsResponse) setLeadFlag(settingsResponse.LeadFlag) if (Boolean(settingsResponse.FieldsRule) && Object.keys(settingsResponse?.FieldsRule).length > 0) { const gottenQuestions = { ...selectedQuestions }; setQuestionsBackend(settingsResponse.FieldsRule); for (let key in settingsResponse.FieldsRule) { if ( settingsResponse.FieldsRule[key as QuestionKeys] !== null ) { const gottenList = settingsResponse.FieldsRule[key as QuestionKeys]; if (gottenList !== null) { Object.keys(gottenList.QuestionID).forEach((qId) => { const q = questions.find(e => e.backendId === Number(qId)) || {} if (gottenQuestions[key as QuestionKeys] === undefined) gottenQuestions[key as QuestionKeys] = [] gottenQuestions[key as QuestionKeys].push({ id: qId, title: q.title, entity: key, }) }) } if (key === "Contact") { const MAP = settingsResponse.FieldsRule[key as QuestionKeys].ContactRuleMap const list = [] for (let key in MAP) { list.push({ id: key, title: FCTranslate[key], entity: "Contact", bitrixId: MAP[key].toString(), }) } setSelectedCurrentFields(list) } } } setSelectedQuestions(gottenQuestions); } if (Boolean(settingsResponse.TagsToAdd) && Object.keys(settingsResponse.TagsToAdd).length > 0) { const gottenTags = { ...selectedTags }; for (let key in settingsResponse.TagsToAdd) { const gottenList = settingsResponse.TagsToAdd[key as TagKeys]; if (gottenList !== null && Array.isArray(gottenList)) { gottenTags[key as TagKeys] = gottenList.map((e) => e.toString()); } } setSelectedTags(gottenTags); } setFirstRules(false); } setIsLoadingPage(false); }; fetchAccountRules(); }, [isModalOpen, isTryRemoveAccount]); useEffect(() => { const transletedQuestions = {...selectedQuestions} Object.keys(selectedQuestions)?.forEach((column) => { selectedQuestions[column].forEach((minifiedData) => { const q = questions.find(e => e.backendId === Number(minifiedData.id)) || {}; transletedQuestions[column].push({ ...minifiedData, title: q.title || transletedQuestions[column].title }) }) }) setSelectedQuestions(transletedQuestions) }, [questions]) useEffect(() => { if (isReadyGetPipeline) { getPipelines({ page: pageOfPipelines, size: SIZE, }).then(([response]) => { if (response && response.items !== null) { const minifiedPipelines: MinifiedData[] = []; response.items.forEach((step) => { minifiedPipelines.push({ id: step.bitrixID.toString(), title: step.name || "Нет названия", }); }); setArrayOfPipelines((prevItems) => [...prevItems, ...minifiedPipelines]); setPageOfPipelinesSteps(1); } else { isReadyGetPipeline = false } }); } }, [pageOfPipelines]); useEffect(() => { if (isReadyGetPipelineStep && selectedPipeline !== null) { const oldData = pageOfPipelinesSteps === 1 ? [] : arrayOfPipelinesSteps; const oldFullData = pageOfPipelinesSteps === 1 ? [] : fullArrayOfPipelinesSteps; getSteps({ page: pageOfPipelinesSteps, size: SIZE, pipelineId: Number(selectedPipeline), }).then(([response]) => { if (response && response.items !== null) { // Фильтруем только нужные элементы const filteredItems = response.items.filter(item => item.entityID === "STATUS" || item.entityID === "SOURCE" || (typeof item.entityID === 'string' && item.entityID.startsWith("DEAL_STAGE")) ); // Минифицируем отфильтрованные данные const minifiedSteps: MinifiedData[] = filteredItems.map((step) => ({ id: step.bitrixID.toString(), title: step.name, entity: step.entityID })); // Обновляем массивы setArrayOfPipelinesSteps([...oldData, ...minifiedSteps]); setFullArrayOfPipelinesSteps([...oldFullData, ...filteredItems]); } else { // Если нет данных, отключаем дальнейшие запросы isReadyGetPipelineStep = false; } }).catch(error => { console.error("Ошибка при получении шагов:", error); isReadyGetPipelineStep = false; }); } }, [selectedPipeline, pageOfPipelinesSteps]); useEffect(() => { if (isReadyGetUsers) { getUsers({ page: pageOfUsers, size: SIZE, }).then(([response]) => { if (response && response.items !== null) { const minifiedUsers: MinifiedData[] = []; response.items.forEach((step) => { minifiedUsers.push({ id: step.bitrixUserID.toString(), title: step.name || "Нет имени", }); }); setArrayOfUsers((prevItems) => [...prevItems, ...minifiedUsers]); } else { isReadyGetUsers = false } }); } }, [pageOfUsers]); // useEffect(() => { // if (isReadyGetTags) { // getTags({ // page: pageOfTags, // size: SIZE, // }).then(([response]) => { // if (response && response.items !== null) { // const minifiedTags: MinifiedData[] = []; // response.items.forEach((step) => { // minifiedTags.push({ // id: step.BitrixID.toString(), // title: step.Name, // entity: // step.Entity === "leads" // ? "Lead" // : step.Entity === "contacts" // ? "Contact" // : step.Entity === "companies" // ? "Company" // : "Customer", // }); // }); // setArrayOfTags((prevItems) => [...prevItems, ...minifiedTags]); // } else { // isReadyGetTags = false // } // }); // } // }, [pageOfTags]); useEffect(() => { if (isReadyGetFields) { getFields({ page: pageOfFields, size: 1000, }).then(([response]) => { if (response && response.items !== null) { const minifiedTags: MinifiedData[] = []; console.log("fields: ") console.log(response.items) const entityMap = { 'CRM_LEAD': 'lead', 'CRM_DEAL': 'deal', 'CRM_COMPANY': 'company', 'CRM_CONTACT': 'contact' }; response.items.forEach((field) => { console.log("поле: ") console.log(field) const entity = entityMap[field.entityID]; if (entity) { minifiedTags.push({ id: field.bitrixID.toString(), title: field.editFromLabel, entity: entity, }); } }); setArrayOfFields((prevItems) => [...prevItems, ...minifiedTags]); } }); } else { isReadyGetFields = false } }, [pageOfFields]); useEffect(() => () => { isReadyGetPipeline = true; isReadyGetPipelineStep = true; isReadyGetUsers = true; isReadyGetTags = true; isReadyGetFields = true; }, []) return { isLoadingPage, firstRules, accountInfo, arrayOfPipelines, arrayOfPipelinesSteps, arrayOfUsers, arrayOfTags, arrayOfFields, selectedPipeline, setSelectedPipeline: selectedPipelineHC, selectedCurrentFields, selectedPipelineStep, setSelectedPipelineStep, selectedDealUser, setSelectedDealPerformer, questionsBackend, selectedTags, setSelectedTags, selectedQuestions, setSelectedQuestions, setPageOfPipelines: () => setPageOfPipelines(old => old + 1), setPageOfPipelinesSteps: () => setPageOfPipelinesSteps(old => old + 1), setPageOfUsers: () => setPageOfUsers(old => old + 1), setPageOfTags: () => setPageOfTags(old => old + 1), setPageOfFields: () => setPageOfFields(old => old + 1), setSelectedCurrentFields, leadFlag, leadFlagHC, fullArrayOfPipelinesSteps }; }; import { makeRequest } from "@frontend/kitui"; const API_URL = `${process.env.REACT_APP_DOMAIN}/squiz/bitrix`; export const resetBitrixTagsFields = async () => { let success = true //Fields try { await makeRequest({ method: "PATCH", url: `${API_URL}/fields`, }); } catch (nativeError) { success = false } //Tags try { await makeRequest({ method: "PATCH", url: `${API_URL}/tags`, }); } catch (nativeError) { success = false } if (success) { enqueueSnackbar("Данные обновятся через 5-30 минут") } else { enqueueSnackbar("Не удалось обновить данные") } }