Merge branch 'dev' into 'staging'
Dev See merge request frontend/squiz!346
This commit is contained in:
commit
bae93b1bf1
@ -1,6 +1,7 @@
|
|||||||
import { QuestionKeys } from "@/pages/IntegrationsPage/IntegrationsModal/types";
|
import { QuestionKeys } from "@/pages/IntegrationsPage/IntegrationsModal/types";
|
||||||
import { makeRequest } from "@api/makeRequest";
|
import { makeRequest } from "@api/makeRequest";
|
||||||
import { parseAxiosError } from "@utils/parse-error";
|
import { parseAxiosError } from "@utils/parse-error";
|
||||||
|
import useSWR from "swr";
|
||||||
|
|
||||||
export type PaginationRequest = {
|
export type PaginationRequest = {
|
||||||
page: number;
|
page: number;
|
||||||
@ -21,6 +22,7 @@ export type AccountResponse = {
|
|||||||
subdomain: string;
|
subdomain: string;
|
||||||
country: string;
|
country: string;
|
||||||
driveURL: string;
|
driveURL: string;
|
||||||
|
stale: boolean;
|
||||||
};
|
};
|
||||||
|
|
||||||
export const getAccount = async (): Promise<[AccountResponse | null, string?]> => {
|
export const getAccount = async (): Promise<[AccountResponse | null, string?]> => {
|
||||||
@ -37,6 +39,16 @@ export const getAccount = async (): Promise<[AccountResponse | null, string?]> =
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
export function useAmoAccount() {
|
||||||
|
return useSWR("amoAccount", () =>
|
||||||
|
makeRequest<void, AccountResponse>({
|
||||||
|
method: "GET",
|
||||||
|
url: `${API_URL}/account`,
|
||||||
|
useToken: true,
|
||||||
|
})
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
// подключить Amo
|
// подключить Amo
|
||||||
|
|
||||||
export const connectAmo = async (): Promise<[string | null, string?]> => {
|
export const connectAmo = async (): Promise<[string | null, string?]> => {
|
||||||
|
|||||||
@ -44,6 +44,7 @@ export const AmoAccountInfo: FC<AmoAccountInfoProps> = ({ handleNextStep, accoun
|
|||||||
<a
|
<a
|
||||||
target="_blank"
|
target="_blank"
|
||||||
href={link}
|
href={link}
|
||||||
|
style={{wordBreak: "break-word"}}
|
||||||
>
|
>
|
||||||
{link}
|
{link}
|
||||||
</a>
|
</a>
|
||||||
|
|||||||
@ -1,5 +1,5 @@
|
|||||||
import React, { FC, useCallback, useEffect, useMemo, useState } from "react";
|
import React, { FC, useCallback, useEffect, useMemo, useState } from "react";
|
||||||
import { Dialog, IconButton, Typography, useMediaQuery, useTheme, Box } from "@mui/material";
|
import {Dialog, IconButton, Typography, useMediaQuery, useTheme, Box, Skeleton} from "@mui/material";
|
||||||
import { useQuestions } from "@/stores/questions/hooks";
|
import { useQuestions } from "@/stores/questions/hooks";
|
||||||
import { redirect } from "react-router-dom";
|
import { redirect } from "react-router-dom";
|
||||||
import { enqueueSnackbar } from "notistack";
|
import { enqueueSnackbar } from "notistack";
|
||||||
@ -73,7 +73,7 @@ export const AmoCRMModal: FC<IntegrationsModalProps> = ({ isModalOpen, handleClo
|
|||||||
const [openDelete, setOpenDelete] = useState<TagQuestionHC | null>(null);
|
const [openDelete, setOpenDelete] = useState<TagQuestionHC | null>(null);
|
||||||
|
|
||||||
const {
|
const {
|
||||||
isloadingPage,
|
isLoadingPage,
|
||||||
firstRules,
|
firstRules,
|
||||||
accountInfo,
|
accountInfo,
|
||||||
arrayOfPipelines,
|
arrayOfPipelines,
|
||||||
@ -360,43 +360,56 @@ export const AmoCRMModal: FC<IntegrationsModalProps> = ({ isModalOpen, handleClo
|
|||||||
flexGrow: 1,
|
flexGrow: 1,
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
<AmoModalTitle
|
{isLoadingPage ?
|
||||||
step={step}
|
<Skeleton
|
||||||
steps={steps}
|
sx={{
|
||||||
isSettingsBlock={isSettingsBlock}
|
width: "100%",
|
||||||
setIsSettingsBlock={setIsSettingsBlock}
|
height: "100%",
|
||||||
setStep={setStep}
|
transform: "none",
|
||||||
startRemoveAccount={() => setIsTryRemoveAccount(true)}
|
}}
|
||||||
/>
|
/> :
|
||||||
{openDelete !== null ? (
|
<>
|
||||||
<AmoDeleteTagQuestion
|
<AmoModalTitle
|
||||||
close={() => setOpenDelete(null)}
|
step={step}
|
||||||
deleteItem={handleDeleteTagQuestion}
|
steps={steps}
|
||||||
/>
|
isSettingsBlock={isSettingsBlock}
|
||||||
) : (
|
|
||||||
<>
|
|
||||||
{isTryRemoveAccount && <AmoRemoveAccount stopThisPage={() => setIsTryRemoveAccount(false)} />}
|
|
||||||
{isSettingsBlock && (
|
|
||||||
<Box sx={{ flexGrow: 1, width: "100%" }}>
|
|
||||||
<AmoSettingsBlock
|
|
||||||
stepTitles={stepTitles}
|
|
||||||
setIsSettingsBlock={setIsSettingsBlock}
|
setIsSettingsBlock={setIsSettingsBlock}
|
||||||
setStep={setStep}
|
setStep={setStep}
|
||||||
selectedDealUser={arrayOfUsers.find((u) => u.id === selectedDealUser)?.title || "не указан"}
|
startRemoveAccount={() => setIsTryRemoveAccount(true)}
|
||||||
selectedFunnel={arrayOfPipelines.find((p) => p.id === selectedPipeline)?.title || "нет данных"}
|
/>
|
||||||
selectedStage={
|
{openDelete !== null ? (
|
||||||
arrayOfPipelinesSteps.find((s) => s.id === selectedPipelineStep)?.title || "нет данных"
|
<AmoDeleteTagQuestion
|
||||||
}
|
close={() => setOpenDelete(null)}
|
||||||
selectedQuestions={selectedQuestions}
|
deleteItem={handleDeleteTagQuestion}
|
||||||
selectedTags={selectedTags}
|
/>
|
||||||
/>
|
) : (
|
||||||
</Box>
|
<>
|
||||||
)}
|
{isTryRemoveAccount && <AmoRemoveAccount stopThisPage={() => setIsTryRemoveAccount(false)} />}
|
||||||
{!isSettingsBlock && !isTryRemoveAccount && (
|
{isSettingsBlock && (
|
||||||
<Box sx={{ flexGrow: 1, width: "100%" }}>{steps[step].component}</Box>
|
<Box sx={{ flexGrow: 1, width: "100%" }}>
|
||||||
)}
|
<AmoSettingsBlock
|
||||||
</>
|
stepTitles={stepTitles}
|
||||||
)}
|
setIsSettingsBlock={setIsSettingsBlock}
|
||||||
|
setStep={setStep}
|
||||||
|
selectedDealUser={arrayOfUsers.find((u) => u.id === selectedDealUser)?.title || "не указан"}
|
||||||
|
selectedFunnel={arrayOfPipelines.find((p) => p.id === selectedPipeline)?.title || "нет данных"}
|
||||||
|
selectedStage={
|
||||||
|
arrayOfPipelinesSteps.find((s) => s.id === selectedPipelineStep)?.title || "нет данных"
|
||||||
|
}
|
||||||
|
selectedQuestions={selectedQuestions}
|
||||||
|
selectedTags={selectedTags}
|
||||||
|
/>
|
||||||
|
</Box>
|
||||||
|
)}
|
||||||
|
{!isSettingsBlock && !isTryRemoveAccount && (
|
||||||
|
<Box sx={{ flexGrow: 1, width: "100%" }}>{steps[step].component}</Box>
|
||||||
|
)}
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</>
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
</Box>
|
</Box>
|
||||||
</Dialog>
|
</Dialog>
|
||||||
);
|
);
|
||||||
|
|||||||
@ -0,0 +1,113 @@
|
|||||||
|
import { connectAmo } from "@/api/integration";
|
||||||
|
import CustomCheckbox from "@/ui_kit/CustomCheckbox";
|
||||||
|
import { Box, Button, Dialog, Typography, useMediaQuery, useTheme } from "@mui/material";
|
||||||
|
import { useState } from "react";
|
||||||
|
|
||||||
|
const HIDE_DIALOG_EXPIRATION_PERIOD = 24 * 60 * 60 * 1000;
|
||||||
|
|
||||||
|
interface Props {
|
||||||
|
initialOpen: boolean;
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function AmoTokenExpiredDialog({ initialOpen }: Props) {
|
||||||
|
const theme = useTheme();
|
||||||
|
const [isDialogOpen, setIsDialogOpen] = useState<boolean>(() => {
|
||||||
|
const hideExpirationTime = Number(localStorage.getItem("hideAmoTokenExpiredDialogExpirationTime"));
|
||||||
|
if (hideExpirationTime && hideExpirationTime > Date.now()) return false;
|
||||||
|
|
||||||
|
return initialOpen;
|
||||||
|
});
|
||||||
|
const [isHideDialogForADayChecked, setIsHideDialogForADayChecked] = useState<boolean>(false);
|
||||||
|
|
||||||
|
const onAmoClick = async () => {
|
||||||
|
const [url, error] = await connectAmo();
|
||||||
|
if (url && !error) {
|
||||||
|
window.open(url, "_blank");
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
function handleDialogClose() {
|
||||||
|
if (isHideDialogForADayChecked) {
|
||||||
|
const expirationDate = Date.now() + HIDE_DIALOG_EXPIRATION_PERIOD;
|
||||||
|
localStorage.setItem("hideAmoTokenExpiredDialogExpirationTime", expirationDate.toString());
|
||||||
|
}
|
||||||
|
|
||||||
|
setIsDialogOpen(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Dialog
|
||||||
|
open={isDialogOpen}
|
||||||
|
onClose={handleDialogClose}
|
||||||
|
PaperProps={{
|
||||||
|
sx: {
|
||||||
|
borderRadius: "12px",
|
||||||
|
maxWidth: "620px",
|
||||||
|
},
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<Box
|
||||||
|
sx={{
|
||||||
|
p: "20px",
|
||||||
|
backgroundColor: "#F2F3F7",
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<Typography
|
||||||
|
color="#4D4D4D"
|
||||||
|
fontSize="24px"
|
||||||
|
fontWeight="medium"
|
||||||
|
>
|
||||||
|
Ваш amo-токен не работает
|
||||||
|
</Typography>
|
||||||
|
</Box>
|
||||||
|
<Box
|
||||||
|
sx={{
|
||||||
|
p: "20px",
|
||||||
|
display: "flex",
|
||||||
|
flexDirection: "column",
|
||||||
|
gap: "30px",
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<Typography color="#4D4D4D">
|
||||||
|
Amo отозвал ваш токен. Зайдите заново в свой аккаунт, чтобы вам снова начали приходить сделки.
|
||||||
|
</Typography>
|
||||||
|
<Box
|
||||||
|
sx={{
|
||||||
|
display: "flex",
|
||||||
|
gap: "10px",
|
||||||
|
[theme.breakpoints.down("sm")]: {
|
||||||
|
flexDirection: "column-reverse",
|
||||||
|
},
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<Button
|
||||||
|
variant="outlined"
|
||||||
|
onClick={handleDialogClose}
|
||||||
|
sx={{
|
||||||
|
flex: "1 0 0",
|
||||||
|
borderColor: "#9A9AAF",
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
Позже
|
||||||
|
</Button>
|
||||||
|
<Button
|
||||||
|
variant="contained"
|
||||||
|
onClick={onAmoClick}
|
||||||
|
sx={{
|
||||||
|
flex: "1 0 0",
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
Перелогиниться
|
||||||
|
</Button>
|
||||||
|
</Box>
|
||||||
|
<CustomCheckbox
|
||||||
|
label={"Не показывать сутки"}
|
||||||
|
checked={isHideDialogForADayChecked}
|
||||||
|
handleChange={({ target }) => {
|
||||||
|
setIsHideDialogForADayChecked(target.checked);
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
</Box>
|
||||||
|
</Dialog>
|
||||||
|
);
|
||||||
|
}
|
||||||
@ -21,7 +21,7 @@ interface Props {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export const useAmoIntegration = ({ isModalOpen, isTryRemoveAccount, quizID }: Props) => {
|
export const useAmoIntegration = ({ isModalOpen, isTryRemoveAccount, quizID }: Props) => {
|
||||||
const [isloadingPage, setIsLoadingPage] = useState<boolean>(true);
|
const [isLoadingPage, setIsLoadingPage] = useState<boolean>(true);
|
||||||
const [firstRules, setFirstRules] = useState<boolean>(false);
|
const [firstRules, setFirstRules] = useState<boolean>(false);
|
||||||
const [accountInfo, setAccountInfo] = useState<AccountResponse | null>(null);
|
const [accountInfo, setAccountInfo] = useState<AccountResponse | null>(null);
|
||||||
|
|
||||||
@ -224,7 +224,7 @@ export const useAmoIntegration = ({ isModalOpen, isTryRemoveAccount, quizID }: P
|
|||||||
}, [pageOfTags]);
|
}, [pageOfTags]);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
isloadingPage,
|
isLoadingPage,
|
||||||
firstRules,
|
firstRules,
|
||||||
accountInfo,
|
accountInfo,
|
||||||
arrayOfPipelines,
|
arrayOfPipelines,
|
||||||
|
|||||||
@ -21,6 +21,8 @@ import { AnyTypedQuizQuestion } from "@frontend/squzanswerer";
|
|||||||
import { ModalInfoWhyCantCreate } from "./ModalInfoWhyCantCreate";
|
import { ModalInfoWhyCantCreate } from "./ModalInfoWhyCantCreate";
|
||||||
import { ConfirmLeaveModal } from "./ConfirmLeaveModal";
|
import { ConfirmLeaveModal } from "./ConfirmLeaveModal";
|
||||||
import { checkQuestionHint } from "@utils/checkQuestionHint";
|
import { checkQuestionHint } from "@utils/checkQuestionHint";
|
||||||
|
import AmoTokenExpiredDialog from "../IntegrationsPage/IntegrationsModal/AmoTokenExpiredDialog";
|
||||||
|
import { useAmoAccount } from "@/api/integration";
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
openBranchingPage: boolean;
|
openBranchingPage: boolean;
|
||||||
@ -41,6 +43,7 @@ export default function EditPage({
|
|||||||
setScrollDown,
|
setScrollDown,
|
||||||
}: Props) {
|
}: Props) {
|
||||||
const quiz = useCurrentQuiz();
|
const quiz = useCurrentQuiz();
|
||||||
|
const { data: amoAccount } = useAmoAccount();
|
||||||
const { editQuizId } = useQuizStore();
|
const { editQuizId } = useQuizStore();
|
||||||
const { questions } = useQuestionsStore();
|
const { questions } = useQuestionsStore();
|
||||||
const { showConfirmLeaveModal, nextStep } = useUiTools();
|
const { showConfirmLeaveModal, nextStep } = useUiTools();
|
||||||
@ -105,6 +108,7 @@ export default function EditPage({
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
|
{amoAccount && <AmoTokenExpiredDialog initialOpen={amoAccount.stale} />}
|
||||||
<Box
|
<Box
|
||||||
sx={{
|
sx={{
|
||||||
display: isMobile ? "block" : "flex",
|
display: isMobile ? "block" : "flex",
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user