feat: marketplaces editor in clients page

This commit is contained in:
2025-10-13 12:47:31 +04:00
parent 2052737561
commit 4a4b05769d
38 changed files with 1461 additions and 12 deletions

View File

@ -1 +1 @@
NEXT_PUBLIC_API_URL=http://your.api/api NEXT_PUBLIC_API_URL=http://test.crm.logidex.ru/api

View File

@ -1,7 +1,7 @@
import { FC } from "react"; import { FC } from "react";
import { Group, TextInput } from "@mantine/core"; import { Group, TextInput } from "@mantine/core";
import { useClientsContext } from "@/app/clients/contexts/ClientsContext"; import { useClientsContext } from "@/app/clients/contexts/ClientsContext";
import useClientsActions from "@/app/clients/hooks/useClientsActions"; import useClientsActions from "@/app/clients/hooks/utils/useClientsActions";
import InlineButton from "@/components/ui/InlineButton/InlineButton"; import InlineButton from "@/components/ui/InlineButton/InlineButton";
const ClientDesktopHeader: FC = () => { const ClientDesktopHeader: FC = () => {

View File

@ -1,7 +1,7 @@
import { FC } from "react"; import { FC } from "react";
import { Flex, TextInput } from "@mantine/core"; import { Flex, TextInput } from "@mantine/core";
import { useClientsContext } from "@/app/clients/contexts/ClientsContext"; import { useClientsContext } from "@/app/clients/contexts/ClientsContext";
import useClientsActions from "@/app/clients/hooks/useClientsActions"; import useClientsActions from "@/app/clients/hooks/utils/useClientsActions";
import InlineButton from "@/components/ui/InlineButton/InlineButton"; import InlineButton from "@/components/ui/InlineButton/InlineButton";
const ClientMobileHeader: FC = () => { const ClientMobileHeader: FC = () => {

View File

@ -3,18 +3,32 @@
import { FC } from "react"; import { FC } from "react";
import { useClientsTableColumns } from "@/app/clients/components/shared/ClientsTable/columns"; import { useClientsTableColumns } from "@/app/clients/components/shared/ClientsTable/columns";
import { useClientsContext } from "@/app/clients/contexts/ClientsContext"; import { useClientsContext } from "@/app/clients/contexts/ClientsContext";
import useClientsActions from "@/app/clients/hooks/useClientsActions"; import useClientsActions from "@/app/clients/hooks/utils/useClientsActions";
import { useProjectsContext } from "@/app/deals/contexts/ProjectsContext";
import BaseTable from "@/components/ui/BaseTable/BaseTable"; import BaseTable from "@/components/ui/BaseTable/BaseTable";
import { useDrawersContext } from "@/drawers/DrawersContext";
import useIsMobile from "@/hooks/utils/useIsMobile"; import useIsMobile from "@/hooks/utils/useIsMobile";
import { ClientSchema } from "@/lib/client";
const ClientsTable: FC = () => { const ClientsTable: FC = () => {
const isMobile = useIsMobile(); const isMobile = useIsMobile();
const { modulesSet } = useProjectsContext();
const { clientsCrud, clients } = useClientsContext(); const { clientsCrud, clients } = useClientsContext();
const { onUpdateClick } = useClientsActions(); const { onUpdateClick } = useClientsActions();
const { openDrawer } = useDrawersContext();
const onOpenMarketplacesList = (client: ClientSchema) => {
openDrawer({
key: "clientMarketplaceDrawer",
props: { client },
});
};
const columns = useClientsTableColumns({ const columns = useClientsTableColumns({
onDelete: clientsCrud.onDelete, onDelete: clientsCrud.onDelete,
onChange: onUpdateClick, onChange: onUpdateClick,
onOpenMarketplacesList,
modulesSet,
}); });
return ( return (

View File

@ -1,15 +1,24 @@
import { useMemo } from "react"; import { useMemo } from "react";
import { IconBasket } from "@tabler/icons-react";
import { DataTableColumn } from "mantine-datatable"; import { DataTableColumn } from "mantine-datatable";
import { Center } from "@mantine/core"; import { Center } from "@mantine/core";
import UpdateDeleteTableActions from "@/components/ui/BaseTable/components/UpdateDeleteTableActions"; import UpdateDeleteTableActions from "@/components/ui/BaseTable/components/UpdateDeleteTableActions";
import { ClientSchema } from "@/lib/client"; import { ClientSchema } from "@/lib/client";
import { ModuleNames } from "@/modules/modules";
type Props = { type Props = {
onChange: (client: ClientSchema) => void; onChange: (client: ClientSchema) => void;
onDelete: (client: ClientSchema) => void; onDelete: (client: ClientSchema) => void;
onOpenMarketplacesList: (client: ClientSchema) => void;
modulesSet: Set<ModuleNames>;
}; };
export const useClientsTableColumns = ({ onChange, onDelete }: Props) => { export const useClientsTableColumns = ({
onChange,
onDelete,
onOpenMarketplacesList,
modulesSet,
}: Props) => {
return useMemo( return useMemo(
() => () =>
[ [
@ -21,6 +30,17 @@ export const useClientsTableColumns = ({ onChange, onDelete }: Props) => {
<UpdateDeleteTableActions <UpdateDeleteTableActions
onDelete={() => onDelete(client)} onDelete={() => onDelete(client)}
onChange={() => onChange(client)} onChange={() => onChange(client)}
otherActions={[
{
label: "Маркетплейсы",
icon: <IconBasket />,
onClick: () =>
onOpenMarketplacesList(client),
hidden: !modulesSet.has(
ModuleNames.FULFILLMENT_BASE
),
},
]}
/> />
), ),
}, },

View File

@ -4,11 +4,11 @@ import { Dispatch, SetStateAction } from "react";
import { import {
ClientsCrud, ClientsCrud,
useClientsCrud, useClientsCrud,
} from "@/app/clients/hooks/useClientsCrud"; } from "@/app/clients/hooks/cruds/useClientsCrud";
import useClientsFilter from "@/app/clients/hooks/useClientsFilter"; import useClientsFilter from "@/app/clients/hooks/utils/useClientsFilter";
import useClientsList from "@/app/clients/hooks/useClientsList";
import { ClientSchema } from "@/lib/client"; import { ClientSchema } from "@/lib/client";
import makeContext from "@/lib/contextFactory/contextFactory"; import makeContext from "@/lib/contextFactory/contextFactory";
import useClientsList from "../hooks/lists/useClientsList";
type ClientsContextState = { type ClientsContextState = {
clients: ClientSchema[]; clients: ClientSchema[];

View File

@ -0,0 +1,50 @@
"use client";
import React, { FC } from "react";
import { Drawer } from "@mantine/core";
import DrawerBody from "@/app/clients/drawers/ClientMarketplacesDrawer/components/DrawerBody";
import { MarketplacesContextProvider } from "@/app/clients/drawers/ClientMarketplacesDrawer/contexts/MarketplacesContext";
import { DrawerProps } from "@/drawers/types";
import useIsMobile from "@/hooks/utils/useIsMobile";
import { ClientSchema } from "@/lib/client";
type Props = {
client: ClientSchema;
};
const ClientMarketplaceDrawer: FC<DrawerProps<Props>> = ({
opened,
onClose,
props,
}) => {
const isMobile = useIsMobile();
return (
<Drawer
size={isMobile ? "100%" : "40%"}
position={"right"}
onClose={onClose}
removeScrollProps={{ allowPinchZoom: true }}
withCloseButton={isMobile}
opened={opened}
trapFocus={false}
title={isMobile ? "Маркетплейсы" : ""}
styles={{
body: {
display: "flex",
flexDirection: "column",
height: isMobile ? "var(--mobile-page-height)" : "100%",
padding: isMobile ? 0 : "var(--mantine-spacing-xs)",
},
header: {
paddingBlock: 0,
},
}}>
<MarketplacesContextProvider client={props.client}>
<DrawerBody />
</MarketplacesContextProvider>
</Drawer>
);
};
export default ClientMarketplaceDrawer;

View File

@ -0,0 +1,53 @@
import { FC } from "react";
import {
ActionIcon,
ComboboxItem,
ComboboxLikeRenderOptionInput,
Image,
} from "@mantine/core";
import useBaseMarketplacesList from "@/app/clients/hooks/lists/useBaseMarketplacesList";
import ObjectSelect, {
ObjectSelectProps,
} from "@/components/selects/ObjectSelect/ObjectSelect";
import { BaseMarketplaceSchema } from "@/lib/client";
type Props = Omit<
ObjectSelectProps<BaseMarketplaceSchema>,
"data" | "getValueFn" | "getLabelFn"
>;
const BaseMarketplaceSelect: FC<Props> = props => {
const { baseMarketplaces } = useBaseMarketplacesList();
const renderOption = (
baseMarketplace: ComboboxLikeRenderOptionInput<ComboboxItem>
) => (
<>
<ActionIcon
radius={"md"}
variant={"transparent"}>
<Image
src={
baseMarketplaces.find(
el =>
baseMarketplace.option.value ===
el.id.toString()
)?.iconUrl || ""
}
/>
</ActionIcon>
{baseMarketplace.option.label}
</>
);
return (
<ObjectSelect
renderOption={renderOption}
getValueFn={baseMarketplace => baseMarketplace.id.toString()}
getLabelFn={baseMarketplace => baseMarketplace.name}
data={baseMarketplaces}
{...props}
/>
);
};
export default BaseMarketplaceSelect;

View File

@ -0,0 +1,18 @@
import React from "react";
import { Flex } from "@mantine/core";
import MarketplacesHeader from "@/app/clients/drawers/ClientMarketplacesDrawer/components/MarketplacesHeader";
import MarketplacesTable from "@/app/clients/drawers/ClientMarketplacesDrawer/components/MarketplacesTable";
const DrawerBody = () => {
return (
<Flex
gap={"xs"}
h={"100%"}
direction={"column"}>
<MarketplacesHeader />
<MarketplacesTable />
</Flex>
);
};
export default DrawerBody;

View File

@ -0,0 +1,21 @@
import { FC } from "react";
import BaseMarketplaceType from "@/modules/dealModularEditorTabs/FulfillmentBase/shared/types/baseMarketplaceType";
import OzonInputs from "./components/OzonInputs";
import WildberriesInputs from "./components/WildberriesInputs";
import YandexMarketInputs from "./components/YandexMarketInputs";
import MpAuthDataInputProps from "./types/MpAuthDataInputProps";
const MarketplaceAuthDataInput: FC<MpAuthDataInputProps> = props => {
switch (props.baseMarketplace.id) {
case BaseMarketplaceType.WILDBERRIES:
return <WildberriesInputs {...props} />;
case BaseMarketplaceType.OZON:
return <OzonInputs {...props} />;
case BaseMarketplaceType.YANDEX_MARKET:
return <YandexMarketInputs {...props} />;
default:
return <></>;
}
};
export default MarketplaceAuthDataInput;

View File

@ -0,0 +1,39 @@
import { FC } from "react";
import { omit } from "lodash";
import { NumberInput, TextInput } from "@mantine/core";
import MpAuthDataInputProps from "../types/MpAuthDataInputProps";
const OzonInputs: FC<MpAuthDataInputProps> = props => {
const restProps = omit(props, ["baseMarketplace"]);
return (
<>
<NumberInput
{...restProps}
label={"Client-Id"}
placeholder={"Введите Client-Id"}
value={props.value?.["Client-Id"] || undefined}
onChange={value =>
props.onChange({
...props.value,
"Client-Id": value.toString(),
})
}
/>
<TextInput
{...restProps}
label={"Api-Key"}
placeholder={"Введите Api-Key"}
value={props.value?.["Api-Key"] || ""}
onChange={value =>
props.onChange({
...props.value,
"Api-Key": value.target.value,
})
}
/>
</>
);
};
export default OzonInputs;

View File

@ -0,0 +1,25 @@
import { FC } from "react";
import { omit } from "lodash";
import { TextInput } from "@mantine/core";
import MpAuthDataInputProps from "../types/MpAuthDataInputProps";
const WildberriesInputs: FC<MpAuthDataInputProps> = props => {
const restProps = omit(props, ["baseMarketplace"]);
return (
<TextInput
{...restProps}
label={"Ключ авторизации"}
placeholder={"Введите ключ авторизации"}
value={props.value?.Authorization || ""}
onChange={value =>
props.onChange({
...props.value,
Authorization: value.target.value,
})
}
/>
);
};
export default WildberriesInputs;

View File

@ -0,0 +1,25 @@
import { FC } from "react";
import { omit } from "lodash";
import { TextInput } from "@mantine/core";
import MpAuthDataInputProps from "../types/MpAuthDataInputProps";
const YandexMarketInputs: FC<MpAuthDataInputProps> = props => {
const restProps = omit(props, ["baseMarketplace"]);
return (
<TextInput
{...restProps}
label={"Api-Key"}
placeholder={"Введите Api-Key"}
value={props.value?.["Api-Key"] || ""}
onChange={value => {
props.onChange({
...props.value,
"Api-Key": value.target.value,
});
}}
/>
);
};
export default YandexMarketInputs;

View File

@ -0,0 +1,12 @@
import BaseFormInputProps from "@/utils/baseFormInputProps";
import { BaseMarketplaceSchema } from "@/lib/client";
type RestProps = {
baseMarketplace: BaseMarketplaceSchema;
};
type MarketplaceAuthData = Record<string, string>;
type MpAuthDataInputProps = BaseFormInputProps<MarketplaceAuthData> & RestProps;
export default MpAuthDataInputProps;

View File

@ -0,0 +1,26 @@
"use client";
import { IconPlus } from "@tabler/icons-react";
import { Group } from "@mantine/core";
import useMarketplacesActions from "@/app/clients/drawers/ClientMarketplacesDrawer/hooks/useMarketplaceActions";
import InlineButton from "@/components/ui/InlineButton/InlineButton";
import useIsMobile from "@/hooks/utils/useIsMobile";
const MarketplacesHeader = () => {
const { onCreateClick } = useMarketplacesActions();
const isMobile = useIsMobile();
return (
<Group>
<InlineButton
onClick={onCreateClick}
mx={isMobile ? "xs" : ""}
w={isMobile ? "100%" : "auto"}>
<IconPlus />
Создать
</InlineButton>
</Group>
);
};
export default MarketplacesHeader;

View File

@ -0,0 +1,44 @@
"use client";
import { IconMoodSad } from "@tabler/icons-react";
import { Group, Text } from "@mantine/core";
import { useMarketplacesContext } from "@/app/clients/drawers/ClientMarketplacesDrawer/contexts/MarketplacesContext";
import useMarketplacesActions from "@/app/clients/drawers/ClientMarketplacesDrawer/hooks/useMarketplaceActions";
import { useMarketplacesTableColumns } from "@/app/clients/drawers/ClientMarketplacesDrawer/hooks/useMarketplacesTableColumns";
import BaseTable from "@/components/ui/BaseTable/BaseTable";
import useIsMobile from "@/hooks/utils/useIsMobile";
const MarketplacesTable = () => {
const isMobile = useIsMobile();
const { onUpdateClick } = useMarketplacesActions();
const { marketplaces, marketplacesCrud } = useMarketplacesContext();
const columns = useMarketplacesTableColumns({
onChange: onUpdateClick,
onDelete: marketplacesCrud.onDelete,
});
return (
<BaseTable
withTableBorder
records={marketplaces}
columns={columns}
groups={undefined}
verticalSpacing={"md"}
mx={isMobile ? "xs" : ""}
styles={{
table: {
height: "100%",
},
}}
emptyState={
<Group mt={marketplaces.length === 0 ? "xl" : 0}>
<Text>Нет маркетплейсов</Text>
<IconMoodSad />
</Group>
}
/>
);
};
export default MarketplacesTable;

View File

@ -0,0 +1,41 @@
"use client";
import {
MarketplacesCrud,
useMarketplacesCrud,
} from "@/app/clients/hooks/cruds/useMarketplacesCrud";
import useMarketplacesList from "@/app/clients/hooks/lists/useMarketplacesList";
import { ClientSchema, MarketplaceSchema } from "@/lib/client";
import makeContext from "@/lib/contextFactory/contextFactory";
type MarketplacesContextState = {
client: ClientSchema;
marketplaces: MarketplaceSchema[];
refetchMarketplaces: () => void;
marketplacesCrud: MarketplacesCrud;
};
type Props = {
client: ClientSchema;
};
const useMarketplacesContextState = ({
client,
}: Props): MarketplacesContextState => {
const marketplacesList = useMarketplacesList({ clientId: client.id });
const marketplacesCrud = useMarketplacesCrud(marketplacesList);
return {
client,
marketplaces: marketplacesList.marketplaces,
refetchMarketplaces: marketplacesList.refetch,
marketplacesCrud,
};
};
export const [MarketplacesContextProvider, useMarketplacesContext] =
makeContext<MarketplacesContextState, Props>(
useMarketplacesContextState,
"Marketplaces"
);

View File

@ -0,0 +1,39 @@
import { modals } from "@mantine/modals";
import { useMarketplacesContext } from "@/app/clients/drawers/ClientMarketplacesDrawer/contexts/MarketplacesContext";
import { MarketplaceSchema } from "@/lib/client";
const useMarketplacesActions = () => {
const { marketplacesCrud, client } = useMarketplacesContext();
const onCreateClick = () => {
modals.openContextModal({
modal: "marketplaceEditorModal",
title: "Создание маркетплейса",
innerProps: {
onCreate: values =>
marketplacesCrud.onCreate({ ...values, client }),
isEditing: false,
},
});
};
const onUpdateClick = (marketplace: MarketplaceSchema) => {
modals.openContextModal({
modal: "marketplaceEditorModal",
title: "Редактирование маркетплейса",
innerProps: {
onChange: updates =>
marketplacesCrud.onUpdate(marketplace.id, updates),
entity: marketplace,
isEditing: true,
},
});
};
return {
onCreateClick,
onUpdateClick,
};
};
export default useMarketplacesActions;

View File

@ -0,0 +1,48 @@
import { useMemo } from "react";
import { DataTableColumn } from "mantine-datatable";
import { ActionIcon, Center, Flex, Image } from "@mantine/core";
import UpdateDeleteTableActions from "@/components/ui/BaseTable/components/UpdateDeleteTableActions";
import { MarketplaceSchema } from "@/lib/client";
type Props = {
onDelete: (mp: MarketplaceSchema) => void;
onChange: (mp: MarketplaceSchema) => void;
};
export const useMarketplacesTableColumns = ({ onDelete, onChange }: Props) => {
return useMemo(
() =>
[
{
accessor: "actions",
title: <Center>Действия</Center>,
width: "0%",
render: mp => (
<UpdateDeleteTableActions
onDelete={() => onDelete(mp)}
onChange={() => onChange(mp)}
/>
),
},
{
title: "Маркетплейс",
accessor: "baseMarketplace",
cellsStyle: () => ({}),
render: mp => (
<Flex key={`${mp.id}mp`}>
<ActionIcon variant={"transparent"}>
<Image
src={mp.baseMarketplace?.iconUrl || ""}
/>
</ActionIcon>
</Flex>
),
},
{
accessor: "name",
title: "Название",
},
] as DataTableColumn<MarketplaceSchema>[],
[]
);
};

View File

@ -0,0 +1,3 @@
import ClientMarketplaceDrawer from "./ClientMarketplacesDrawer";
export default ClientMarketplaceDrawer;

View File

@ -0,0 +1,87 @@
"use client";
import { Stack, TextInput } from "@mantine/core";
import { useForm } from "@mantine/form";
import { ContextModalProps } from "@mantine/modals";
import BaseMarketplaceSelect from "@/app/clients/drawers/ClientMarketplacesDrawer/components/BaseMarketplaceSelect";
import MarketplaceAuthDataInput from "@/app/clients/drawers/ClientMarketplacesDrawer/components/MarketplaceAuthDataInput/MarketplaceAuthDataInput";
import {
CreateMarketplaceSchema,
MarketplaceSchema,
UpdateMarketplaceSchema,
} from "@/lib/client";
import BaseFormModal, {
CreateEditFormProps,
} from "@/modals/base/BaseFormModal/BaseFormModal";
type Props = CreateEditFormProps<
MarketplaceSchema,
CreateMarketplaceSchema,
UpdateMarketplaceSchema
>;
const MarketplaceEditorModal = ({
context,
id,
innerProps,
}: ContextModalProps<Props>) => {
const initialValues: UpdateMarketplaceSchema | CreateMarketplaceSchema =
innerProps.isEditing
? innerProps.entity
: {
name: "",
authData: {
"Authorization": "",
"Client-Id": "",
"Api-Key": "",
"CampaignId": "",
},
};
const form = useForm({
initialValues,
validate: {
name: name =>
(!name || name.trim() === "") &&
"Необходимо ввести название маркетплейса",
baseMarketplace: baseMarketplace =>
!baseMarketplace && "Необходимо указать базовый маркетплейс",
authData: authData =>
!authData && "Необходимо указать данные авторизации",
},
});
return (
<BaseFormModal
{...innerProps}
closeOnSubmit
form={form}
onClose={() => context.closeContextModal(id)}>
<Stack gap={"xs"}>
<TextInput
label={"Название"}
placeholder={"Введите название маркетплейса"}
{...form.getInputProps("name")}
/>
<BaseMarketplaceSelect
label={"Базовый маркетплейс"}
placeholder={"Выберите базовый маркетплейс"}
{...form.getInputProps("baseMarketplace")}
/>
{form.values.baseMarketplace && (
<MarketplaceAuthDataInput
baseMarketplace={form.values.baseMarketplace}
value={form.values.authData as Record<string, string>}
onChange={value =>
form.setFieldValue("authData", value)
}
error={form.getInputProps("authData").error}
/>
)}
</Stack>
</BaseFormModal>
);
};
export default MarketplaceEditorModal;

View File

@ -0,0 +1,50 @@
import { useCrudOperations } from "@/hooks/cruds/baseCrud";
import {
CreateMarketplaceSchema,
MarketplaceSchema,
UpdateMarketplaceSchema,
} from "@/lib/client";
import {
createMarketplaceMutation,
deleteMarketplaceMutation,
updateMarketplaceMutation,
} from "@/lib/client/@tanstack/react-query.gen";
type UseMarketplacesProps = {
queryKey: any[];
};
export type MarketplacesCrud = {
onCreate: (mp: CreateMarketplaceSchema) => void;
onUpdate: (
mpId: number,
mp: UpdateMarketplaceSchema,
onSuccess?: () => void
) => void;
onDelete: (mp: MarketplaceSchema) => void;
};
export const useMarketplacesCrud = ({
queryKey,
}: UseMarketplacesProps): MarketplacesCrud => {
return useCrudOperations<
MarketplaceSchema,
UpdateMarketplaceSchema,
CreateMarketplaceSchema
>({
key: "getMarketplaces",
queryKey,
mutations: {
create: createMarketplaceMutation(),
update: updateMarketplaceMutation(),
delete: deleteMarketplaceMutation(),
},
getUpdateEntity: (old, update) => ({
...old,
baseMarketplace: update.baseMarketplace ?? old.baseMarketplace,
name: update.name ?? old.name,
authData: update.authData ?? old.authData,
}),
getDeleteConfirmTitle: () => "Удаление маркетплейса",
});
};

View File

@ -0,0 +1,15 @@
import { useQuery } from "@tanstack/react-query";
import {
getBaseMarketplacesOptions,
getBaseMarketplacesQueryKey,
} from "@/lib/client/@tanstack/react-query.gen";
const useBaseMarketplacesList = () => {
const { data, refetch } = useQuery(getBaseMarketplacesOptions());
const queryKey = getBaseMarketplacesQueryKey();
return { baseMarketplaces: data?.items ?? [], refetch, queryKey };
};
export default useBaseMarketplacesList;

View File

@ -0,0 +1,21 @@
import { useQuery } from "@tanstack/react-query";
import {
getMarketplacesOptions,
getMarketplacesQueryKey,
} from "@/lib/client/@tanstack/react-query.gen";
type Props = {
clientId: number;
};
const useMarketplacesList = ({ clientId }: Props) => {
const { data, refetch } = useQuery(
getMarketplacesOptions({ path: { clientId } })
);
const queryKey = getMarketplacesQueryKey({ path: { clientId } });
return { marketplaces: data?.items ?? [], refetch, queryKey };
};
export default useMarketplacesList;

View File

@ -1,4 +1,4 @@
import React, { CSSProperties, FC } from "react"; import React, { CSSProperties, FC, ReactNode } from "react";
import { IconDotsVertical, IconEdit, IconTrash } from "@tabler/icons-react"; import { IconDotsVertical, IconEdit, IconTrash } from "@tabler/icons-react";
import { Box, Flex, Menu } from "@mantine/core"; import { Box, Flex, Menu } from "@mantine/core";
import ActionIconWithTip from "@/components/ui/ActionIconWithTip/ActionIconWithTip"; import ActionIconWithTip from "@/components/ui/ActionIconWithTip/ActionIconWithTip";
@ -6,9 +6,17 @@ import DropdownMenuItem from "@/components/ui/DropdownMenuItem/DropdownMenuItem"
import ThemeIcon from "@/components/ui/ThemeIcon/ThemeIcon"; import ThemeIcon from "@/components/ui/ThemeIcon/ThemeIcon";
import useIsMobile from "@/hooks/utils/useIsMobile"; import useIsMobile from "@/hooks/utils/useIsMobile";
export type ActionData = {
icon: ReactNode;
onClick: () => void;
label: string;
hidden?: boolean;
};
type Props = { type Props = {
onChange: () => void; onChange: () => void;
onDelete: () => void; onDelete: () => void;
otherActions?: ActionData[];
dotsForMobile?: boolean; dotsForMobile?: boolean;
style?: CSSProperties; style?: CSSProperties;
}; };
@ -16,6 +24,7 @@ type Props = {
const UpdateDeleteTableActions: FC<Props> = ({ const UpdateDeleteTableActions: FC<Props> = ({
onChange, onChange,
onDelete, onDelete,
otherActions,
style, style,
dotsForMobile = false, dotsForMobile = false,
}) => { }) => {
@ -37,6 +46,17 @@ const UpdateDeleteTableActions: FC<Props> = ({
icon={<IconEdit />} icon={<IconEdit />}
label={"Редактировать"} label={"Редактировать"}
/> />
{otherActions?.map(
action =>
!action.hidden && (
<DropdownMenuItem
onClick={action.onClick}
icon={action.icon}
label={action.label}
key={action.label}
/>
)
)}
<DropdownMenuItem <DropdownMenuItem
onClick={onDelete} onClick={onDelete}
icon={<IconTrash />} icon={<IconTrash />}
@ -59,6 +79,20 @@ const UpdateDeleteTableActions: FC<Props> = ({
tipLabel={"Редактировать"}> tipLabel={"Редактировать"}>
<IconEdit /> <IconEdit />
</ActionIconWithTip> </ActionIconWithTip>
{otherActions?.map(
action =>
!action.hidden && (
<ActionIconWithTip
onClick={e => {
e.stopPropagation();
action.onClick();
}}
key={action.label}
tipLabel={action.label}>
{action.icon}
</ActionIconWithTip>
)
)}
<ActionIconWithTip <ActionIconWithTip
color={"red"} color={"red"}
onClick={e => { onClick={e => {

View File

@ -1,8 +1,9 @@
import ClientMarketplaceDrawer from "@/app/clients/drawers/ClientMarketplacesDrawer";
import BoardsMobileEditorDrawer from "@/app/deals/drawers/BoardsMobileEditorDrawer"; import BoardsMobileEditorDrawer from "@/app/deals/drawers/BoardsMobileEditorDrawer";
import StatusesMobileEditorDrawer from "../app/deals/drawers/StatusesMobileEditorDrawer";
import DealEditorDrawer from "@/app/deals/drawers/DealEditorDrawer"; import DealEditorDrawer from "@/app/deals/drawers/DealEditorDrawer";
import ProjectEditorDrawer from "@/app/deals/drawers/ProjectEditorDrawer"; import ProjectEditorDrawer from "@/app/deals/drawers/ProjectEditorDrawer";
import ProjectsMobileEditorDrawer from "@/app/deals/drawers/ProjectsMobileEditorDrawer"; import ProjectsMobileEditorDrawer from "@/app/deals/drawers/ProjectsMobileEditorDrawer";
import StatusesMobileEditorDrawer from "../app/deals/drawers/StatusesMobileEditorDrawer";
const drawerRegistry = { const drawerRegistry = {
projectsMobileEditorDrawer: ProjectsMobileEditorDrawer, projectsMobileEditorDrawer: ProjectsMobileEditorDrawer,
@ -10,6 +11,7 @@ const drawerRegistry = {
boardsMobileEditorDrawer: BoardsMobileEditorDrawer, boardsMobileEditorDrawer: BoardsMobileEditorDrawer,
dealEditorDrawer: DealEditorDrawer, dealEditorDrawer: DealEditorDrawer,
projectEditorDrawer: ProjectEditorDrawer, projectEditorDrawer: ProjectEditorDrawer,
clientMarketplaceDrawer: ClientMarketplaceDrawer,
}; };
export default drawerRegistry; export default drawerRegistry;

View File

@ -18,6 +18,7 @@ import {
createDealProduct, createDealProduct,
createDealProductService, createDealProductService,
createDealService, createDealService,
createMarketplace,
createProduct, createProduct,
createProject, createProject,
createService, createService,
@ -31,6 +32,7 @@ import {
deleteDealProduct, deleteDealProduct,
deleteDealProductService, deleteDealProductService,
deleteDealService, deleteDealService,
deleteMarketplace,
deleteProduct, deleteProduct,
deleteProject, deleteProject,
deleteService, deleteService,
@ -41,12 +43,14 @@ import {
getBarcodeTemplateAttributes, getBarcodeTemplateAttributes,
getBarcodeTemplates, getBarcodeTemplates,
getBarcodeTemplateSizes, getBarcodeTemplateSizes,
getBaseMarketplaces,
getBoards, getBoards,
getBuiltInModules, getBuiltInModules,
getClients, getClients,
getDealProducts, getDealProducts,
getDeals, getDeals,
getDealServices, getDealServices,
getMarketplaces,
getProductBarcodePdf, getProductBarcodePdf,
getProducts, getProducts,
getProjects, getProjects,
@ -62,6 +66,7 @@ import {
updateDealProduct, updateDealProduct,
updateDealProductService, updateDealProductService,
updateDealService, updateDealService,
updateMarketplace,
updateProduct, updateProduct,
updateProject, updateProject,
updateService, updateService,
@ -98,6 +103,9 @@ import type {
CreateDealServiceData, CreateDealServiceData,
CreateDealServiceError, CreateDealServiceError,
CreateDealServiceResponse2, CreateDealServiceResponse2,
CreateMarketplaceData,
CreateMarketplaceError,
CreateMarketplaceResponse2,
CreateProductData, CreateProductData,
CreateProductError, CreateProductError,
CreateProductResponse2, CreateProductResponse2,
@ -137,6 +145,9 @@ import type {
DeleteDealServiceData, DeleteDealServiceData,
DeleteDealServiceError, DeleteDealServiceError,
DeleteDealServiceResponse2, DeleteDealServiceResponse2,
DeleteMarketplaceData,
DeleteMarketplaceError,
DeleteMarketplaceResponse2,
DeleteProductData, DeleteProductData,
DeleteProductError, DeleteProductError,
DeleteProductResponse2, DeleteProductResponse2,
@ -161,6 +172,7 @@ import type {
GetBarcodeTemplateAttributesData, GetBarcodeTemplateAttributesData,
GetBarcodeTemplatesData, GetBarcodeTemplatesData,
GetBarcodeTemplateSizesData, GetBarcodeTemplateSizesData,
GetBaseMarketplacesData,
GetBoardsData, GetBoardsData,
GetBuiltInModulesData, GetBuiltInModulesData,
GetClientsData, GetClientsData,
@ -169,6 +181,7 @@ import type {
GetDealsError, GetDealsError,
GetDealServicesData, GetDealServicesData,
GetDealsResponse2, GetDealsResponse2,
GetMarketplacesData,
GetProductBarcodePdfData, GetProductBarcodePdfData,
GetProductBarcodePdfError, GetProductBarcodePdfError,
GetProductBarcodePdfResponse2, GetProductBarcodePdfResponse2,
@ -202,6 +215,9 @@ import type {
UpdateDealServiceData, UpdateDealServiceData,
UpdateDealServiceError, UpdateDealServiceError,
UpdateDealServiceResponse2, UpdateDealServiceResponse2,
UpdateMarketplaceData,
UpdateMarketplaceError,
UpdateMarketplaceResponse2,
UpdateProductData, UpdateProductData,
UpdateProductError, UpdateProductError,
UpdateProductResponse2, UpdateProductResponse2,
@ -1696,6 +1712,159 @@ export const addKitToDealMutation = (
return mutationOptions; return mutationOptions;
}; };
export const getBaseMarketplacesQueryKey = (
options?: Options<GetBaseMarketplacesData>
) => createQueryKey("getBaseMarketplaces", options);
/**
* Get Base Marketplaces
*/
export const getBaseMarketplacesOptions = (
options?: Options<GetBaseMarketplacesData>
) => {
return queryOptions({
queryFn: async ({ queryKey, signal }) => {
const { data } = await getBaseMarketplaces({
...options,
...queryKey[0],
signal,
throwOnError: true,
});
return data;
},
queryKey: getBaseMarketplacesQueryKey(options),
});
};
export const getMarketplacesQueryKey = (
options: Options<GetMarketplacesData>
) => createQueryKey("getMarketplaces", options);
/**
* Get Marketplaces
*/
export const getMarketplacesOptions = (
options: Options<GetMarketplacesData>
) => {
return queryOptions({
queryFn: async ({ queryKey, signal }) => {
const { data } = await getMarketplaces({
...options,
...queryKey[0],
signal,
throwOnError: true,
});
return data;
},
queryKey: getMarketplacesQueryKey(options),
});
};
export const createMarketplaceQueryKey = (
options: Options<CreateMarketplaceData>
) => createQueryKey("createMarketplace", options);
/**
* Create Product
*/
export const createMarketplaceOptions = (
options: Options<CreateMarketplaceData>
) => {
return queryOptions({
queryFn: async ({ queryKey, signal }) => {
const { data } = await createMarketplace({
...options,
...queryKey[0],
signal,
throwOnError: true,
});
return data;
},
queryKey: createMarketplaceQueryKey(options),
});
};
/**
* Create Product
*/
export const createMarketplaceMutation = (
options?: Partial<Options<CreateMarketplaceData>>
): UseMutationOptions<
CreateMarketplaceResponse2,
AxiosError<CreateMarketplaceError>,
Options<CreateMarketplaceData>
> => {
const mutationOptions: UseMutationOptions<
CreateMarketplaceResponse2,
AxiosError<CreateMarketplaceError>,
Options<CreateMarketplaceData>
> = {
mutationFn: async localOptions => {
const { data } = await createMarketplace({
...options,
...localOptions,
throwOnError: true,
});
return data;
},
};
return mutationOptions;
};
/**
* Delete Marketplace
*/
export const deleteMarketplaceMutation = (
options?: Partial<Options<DeleteMarketplaceData>>
): UseMutationOptions<
DeleteMarketplaceResponse2,
AxiosError<DeleteMarketplaceError>,
Options<DeleteMarketplaceData>
> => {
const mutationOptions: UseMutationOptions<
DeleteMarketplaceResponse2,
AxiosError<DeleteMarketplaceError>,
Options<DeleteMarketplaceData>
> = {
mutationFn: async localOptions => {
const { data } = await deleteMarketplace({
...options,
...localOptions,
throwOnError: true,
});
return data;
},
};
return mutationOptions;
};
/**
* Update Marketplace
*/
export const updateMarketplaceMutation = (
options?: Partial<Options<UpdateMarketplaceData>>
): UseMutationOptions<
UpdateMarketplaceResponse2,
AxiosError<UpdateMarketplaceError>,
Options<UpdateMarketplaceData>
> => {
const mutationOptions: UseMutationOptions<
UpdateMarketplaceResponse2,
AxiosError<UpdateMarketplaceError>,
Options<UpdateMarketplaceData>
> = {
mutationFn: async localOptions => {
const { data } = await updateMarketplace({
...options,
...localOptions,
throwOnError: true,
});
return data;
},
};
return mutationOptions;
};
export const getProductsQueryKey = (options?: Options<GetProductsData>) => export const getProductsQueryKey = (options?: Options<GetProductsData>) =>
createQueryKey("getProducts", options); createQueryKey("getProducts", options);

View File

@ -30,6 +30,9 @@ import type {
CreateDealServiceData, CreateDealServiceData,
CreateDealServiceErrors, CreateDealServiceErrors,
CreateDealServiceResponses, CreateDealServiceResponses,
CreateMarketplaceData,
CreateMarketplaceErrors,
CreateMarketplaceResponses,
CreateProductData, CreateProductData,
CreateProductErrors, CreateProductErrors,
CreateProductResponses, CreateProductResponses,
@ -69,6 +72,9 @@ import type {
DeleteDealServiceData, DeleteDealServiceData,
DeleteDealServiceErrors, DeleteDealServiceErrors,
DeleteDealServiceResponses, DeleteDealServiceResponses,
DeleteMarketplaceData,
DeleteMarketplaceErrors,
DeleteMarketplaceResponses,
DeleteProductData, DeleteProductData,
DeleteProductErrors, DeleteProductErrors,
DeleteProductResponses, DeleteProductResponses,
@ -96,6 +102,8 @@ import type {
GetBarcodeTemplateSizesData, GetBarcodeTemplateSizesData,
GetBarcodeTemplateSizesResponses, GetBarcodeTemplateSizesResponses,
GetBarcodeTemplatesResponses, GetBarcodeTemplatesResponses,
GetBaseMarketplacesData,
GetBaseMarketplacesResponses,
GetBoardsData, GetBoardsData,
GetBoardsErrors, GetBoardsErrors,
GetBoardsResponses, GetBoardsResponses,
@ -113,6 +121,9 @@ import type {
GetDealServicesErrors, GetDealServicesErrors,
GetDealServicesResponses, GetDealServicesResponses,
GetDealsResponses, GetDealsResponses,
GetMarketplacesData,
GetMarketplacesErrors,
GetMarketplacesResponses,
GetProductBarcodePdfData, GetProductBarcodePdfData,
GetProductBarcodePdfErrors, GetProductBarcodePdfErrors,
GetProductBarcodePdfResponses, GetProductBarcodePdfResponses,
@ -154,6 +165,9 @@ import type {
UpdateDealServiceData, UpdateDealServiceData,
UpdateDealServiceErrors, UpdateDealServiceErrors,
UpdateDealServiceResponses, UpdateDealServiceResponses,
UpdateMarketplaceData,
UpdateMarketplaceErrors,
UpdateMarketplaceResponses,
UpdateProductData, UpdateProductData,
UpdateProductErrors, UpdateProductErrors,
UpdateProductResponses, UpdateProductResponses,
@ -192,6 +206,8 @@ import {
zCreateDealResponse2, zCreateDealResponse2,
zCreateDealServiceData, zCreateDealServiceData,
zCreateDealServiceResponse2, zCreateDealServiceResponse2,
zCreateMarketplaceData,
zCreateMarketplaceResponse2,
zCreateProductData, zCreateProductData,
zCreateProductResponse2, zCreateProductResponse2,
zCreateProjectData, zCreateProjectData,
@ -218,6 +234,8 @@ import {
zDeleteDealResponse2, zDeleteDealResponse2,
zDeleteDealServiceData, zDeleteDealServiceData,
zDeleteDealServiceResponse2, zDeleteDealServiceResponse2,
zDeleteMarketplaceData,
zDeleteMarketplaceResponse2,
zDeleteProductData, zDeleteProductData,
zDeleteProductResponse2, zDeleteProductResponse2,
zDeleteProjectData, zDeleteProjectData,
@ -238,6 +256,8 @@ import {
zGetBarcodeTemplateSizesData, zGetBarcodeTemplateSizesData,
zGetBarcodeTemplateSizesResponse2, zGetBarcodeTemplateSizesResponse2,
zGetBarcodeTemplatesResponse2, zGetBarcodeTemplatesResponse2,
zGetBaseMarketplacesData,
zGetBaseMarketplacesResponse2,
zGetBoardsData, zGetBoardsData,
zGetBoardsResponse2, zGetBoardsResponse2,
zGetBuiltInModulesData, zGetBuiltInModulesData,
@ -250,6 +270,8 @@ import {
zGetDealServicesData, zGetDealServicesData,
zGetDealServicesResponse2, zGetDealServicesResponse2,
zGetDealsResponse2, zGetDealsResponse2,
zGetMarketplacesData,
zGetMarketplacesResponse2,
zGetProductBarcodePdfData, zGetProductBarcodePdfData,
zGetProductBarcodePdfResponse2, zGetProductBarcodePdfResponse2,
zGetProductsData, zGetProductsData,
@ -280,6 +302,8 @@ import {
zUpdateDealResponse2, zUpdateDealResponse2,
zUpdateDealServiceData, zUpdateDealServiceData,
zUpdateDealServiceResponse2, zUpdateDealServiceResponse2,
zUpdateMarketplaceData,
zUpdateMarketplaceResponse2,
zUpdateProductData, zUpdateProductData,
zUpdateProductResponse2, zUpdateProductResponse2,
zUpdateProjectData, zUpdateProjectData,
@ -1363,6 +1387,129 @@ export const addKitToDeal = <ThrowOnError extends boolean = false>(
}); });
}; };
/**
* Get Base Marketplaces
*/
export const getBaseMarketplaces = <ThrowOnError extends boolean = false>(
options?: Options<GetBaseMarketplacesData, ThrowOnError>
) => {
return (options?.client ?? _heyApiClient).get<
GetBaseMarketplacesResponses,
unknown,
ThrowOnError
>({
requestValidator: async data => {
return await zGetBaseMarketplacesData.parseAsync(data);
},
responseType: "json",
responseValidator: async data => {
return await zGetBaseMarketplacesResponse2.parseAsync(data);
},
url: "/modules/fulfillment-base/marketplace/base",
...options,
});
};
/**
* Get Marketplaces
*/
export const getMarketplaces = <ThrowOnError extends boolean = false>(
options: Options<GetMarketplacesData, ThrowOnError>
) => {
return (options.client ?? _heyApiClient).get<
GetMarketplacesResponses,
GetMarketplacesErrors,
ThrowOnError
>({
requestValidator: async data => {
return await zGetMarketplacesData.parseAsync(data);
},
responseType: "json",
responseValidator: async data => {
return await zGetMarketplacesResponse2.parseAsync(data);
},
url: "/modules/fulfillment-base/marketplace/{clientId}",
...options,
});
};
/**
* Create Product
*/
export const createMarketplace = <ThrowOnError extends boolean = false>(
options: Options<CreateMarketplaceData, ThrowOnError>
) => {
return (options.client ?? _heyApiClient).post<
CreateMarketplaceResponses,
CreateMarketplaceErrors,
ThrowOnError
>({
requestValidator: async data => {
return await zCreateMarketplaceData.parseAsync(data);
},
responseType: "json",
responseValidator: async data => {
return await zCreateMarketplaceResponse2.parseAsync(data);
},
url: "/modules/fulfillment-base/marketplace/",
...options,
headers: {
"Content-Type": "application/json",
...options.headers,
},
});
};
/**
* Delete Marketplace
*/
export const deleteMarketplace = <ThrowOnError extends boolean = false>(
options: Options<DeleteMarketplaceData, ThrowOnError>
) => {
return (options.client ?? _heyApiClient).delete<
DeleteMarketplaceResponses,
DeleteMarketplaceErrors,
ThrowOnError
>({
requestValidator: async data => {
return await zDeleteMarketplaceData.parseAsync(data);
},
responseType: "json",
responseValidator: async data => {
return await zDeleteMarketplaceResponse2.parseAsync(data);
},
url: "/modules/fulfillment-base/marketplace/{pk}",
...options,
});
};
/**
* Update Marketplace
*/
export const updateMarketplace = <ThrowOnError extends boolean = false>(
options: Options<UpdateMarketplaceData, ThrowOnError>
) => {
return (options.client ?? _heyApiClient).patch<
UpdateMarketplaceResponses,
UpdateMarketplaceErrors,
ThrowOnError
>({
requestValidator: async data => {
return await zUpdateMarketplaceData.parseAsync(data);
},
responseType: "json",
responseValidator: async data => {
return await zUpdateMarketplaceResponse2.parseAsync(data);
},
url: "/modules/fulfillment-base/marketplace/{pk}",
...options,
headers: {
"Content-Type": "application/json",
...options.headers,
},
});
};
/** /**
* Get Products * Get Products
*/ */

View File

@ -63,6 +63,24 @@ export type BarcodeTemplateSizeSchema = {
height: number; height: number;
}; };
/**
* BaseMarketplaceSchema
*/
export type BaseMarketplaceSchema = {
/**
* Id
*/
id: number;
/**
* Name
*/
name: string;
/**
* Iconurl
*/
iconUrl: string;
};
/** /**
* BoardSchema * BoardSchema
*/ */
@ -453,6 +471,42 @@ export type CreateDealServiceSchema = {
price: number; price: number;
}; };
/**
* CreateMarketplaceRequest
*/
export type CreateMarketplaceRequest = {
entity: CreateMarketplaceSchema;
};
/**
* CreateMarketplaceResponse
*/
export type CreateMarketplaceResponse = {
/**
* Message
*/
message: string;
entity: MarketplaceSchema;
};
/**
* CreateMarketplaceSchema
*/
export type CreateMarketplaceSchema = {
baseMarketplace: BaseMarketplaceSchema;
client: ClientSchema;
/**
* Name
*/
name: string;
/**
* Authdata
*/
authData: {
[key: string]: unknown;
};
};
/** /**
* CreateProductRequest * CreateProductRequest
*/ */
@ -953,6 +1007,16 @@ export type DeleteDealServiceResponse = {
message: string; message: string;
}; };
/**
* DeleteMarketplaceResponse
*/
export type DeleteMarketplaceResponse = {
/**
* Message
*/
message: string;
};
/** /**
* DeleteProductResponse * DeleteProductResponse
*/ */
@ -1063,6 +1127,16 @@ export type GetBarcodeTemplatesResponse = {
items: Array<BarcodeTemplateSchema>; items: Array<BarcodeTemplateSchema>;
}; };
/**
* GetBaseMarketplacesResponse
*/
export type GetBaseMarketplacesResponse = {
/**
* Items
*/
items: Array<BaseMarketplaceSchema>;
};
/** /**
* GetBoardsResponse * GetBoardsResponse
*/ */
@ -1114,6 +1188,16 @@ export type GetDealsResponse = {
paginationInfo: PaginationInfoSchema; paginationInfo: PaginationInfoSchema;
}; };
/**
* GetMarketplacesResponse
*/
export type GetMarketplacesResponse = {
/**
* Items
*/
items: Array<MarketplaceSchema>;
};
/** /**
* GetProductBarcodePdfRequest * GetProductBarcodePdfRequest
*/ */
@ -1231,6 +1315,32 @@ export type HttpValidationError = {
detail?: Array<ValidationError>; detail?: Array<ValidationError>;
}; };
/**
* MarketplaceSchema
*/
export type MarketplaceSchema = {
/**
* Id
*/
id: number;
/**
* Basemarketplaceid
*/
baseMarketplaceId: number;
baseMarketplace: BaseMarketplaceSchema;
client: ClientSchema;
/**
* Name
*/
name: string;
/**
* Authdata
*/
authData: {
[key: string]: unknown;
};
};
/** /**
* PaginationInfoSchema * PaginationInfoSchema
*/ */
@ -1749,6 +1859,41 @@ export type UpdateDealServiceSchema = {
isFixedPrice: boolean; isFixedPrice: boolean;
}; };
/**
* UpdateMarketplaceRequest
*/
export type UpdateMarketplaceRequest = {
entity: UpdateMarketplaceSchema;
};
/**
* UpdateMarketplaceResponse
*/
export type UpdateMarketplaceResponse = {
/**
* Message
*/
message: string;
};
/**
* UpdateMarketplaceSchema
*/
export type UpdateMarketplaceSchema = {
baseMarketplace?: BaseMarketplaceSchema | null;
client?: ClientSchema | null;
/**
* Name
*/
name?: string | null;
/**
* Authdata
*/
authData?: {
[key: string]: unknown;
} | null;
};
/** /**
* UpdateProductRequest * UpdateProductRequest
*/ */
@ -3304,6 +3449,146 @@ export type AddKitToDealResponses = {
export type AddKitToDealResponse = export type AddKitToDealResponse =
AddKitToDealResponses[keyof AddKitToDealResponses]; AddKitToDealResponses[keyof AddKitToDealResponses];
export type GetBaseMarketplacesData = {
body?: never;
path?: never;
query?: never;
url: "/modules/fulfillment-base/marketplace/base";
};
export type GetBaseMarketplacesResponses = {
/**
* Successful Response
*/
200: GetBaseMarketplacesResponse;
};
export type GetBaseMarketplacesResponse2 =
GetBaseMarketplacesResponses[keyof GetBaseMarketplacesResponses];
export type GetMarketplacesData = {
body?: never;
path: {
/**
* Clientid
*/
clientId: number;
};
query?: never;
url: "/modules/fulfillment-base/marketplace/{clientId}";
};
export type GetMarketplacesErrors = {
/**
* Validation Error
*/
422: HttpValidationError;
};
export type GetMarketplacesError =
GetMarketplacesErrors[keyof GetMarketplacesErrors];
export type GetMarketplacesResponses = {
/**
* Successful Response
*/
200: GetMarketplacesResponse;
};
export type GetMarketplacesResponse2 =
GetMarketplacesResponses[keyof GetMarketplacesResponses];
export type CreateMarketplaceData = {
body: CreateMarketplaceRequest;
path?: never;
query?: never;
url: "/modules/fulfillment-base/marketplace/";
};
export type CreateMarketplaceErrors = {
/**
* Validation Error
*/
422: HttpValidationError;
};
export type CreateMarketplaceError =
CreateMarketplaceErrors[keyof CreateMarketplaceErrors];
export type CreateMarketplaceResponses = {
/**
* Successful Response
*/
200: CreateMarketplaceResponse;
};
export type CreateMarketplaceResponse2 =
CreateMarketplaceResponses[keyof CreateMarketplaceResponses];
export type DeleteMarketplaceData = {
body?: never;
path: {
/**
* Pk
*/
pk: number;
};
query?: never;
url: "/modules/fulfillment-base/marketplace/{pk}";
};
export type DeleteMarketplaceErrors = {
/**
* Validation Error
*/
422: HttpValidationError;
};
export type DeleteMarketplaceError =
DeleteMarketplaceErrors[keyof DeleteMarketplaceErrors];
export type DeleteMarketplaceResponses = {
/**
* Successful Response
*/
200: DeleteMarketplaceResponse;
};
export type DeleteMarketplaceResponse2 =
DeleteMarketplaceResponses[keyof DeleteMarketplaceResponses];
export type UpdateMarketplaceData = {
body: UpdateMarketplaceRequest;
path: {
/**
* Pk
*/
pk: number;
};
query?: never;
url: "/modules/fulfillment-base/marketplace/{pk}";
};
export type UpdateMarketplaceErrors = {
/**
* Validation Error
*/
422: HttpValidationError;
};
export type UpdateMarketplaceError =
UpdateMarketplaceErrors[keyof UpdateMarketplaceErrors];
export type UpdateMarketplaceResponses = {
/**
* Successful Response
*/
200: UpdateMarketplaceResponse;
};
export type UpdateMarketplaceResponse2 =
UpdateMarketplaceResponses[keyof UpdateMarketplaceResponses];
export type GetProductsData = { export type GetProductsData = {
body?: never; body?: never;
path?: never; path?: never;

View File

@ -32,6 +32,15 @@ export const zBarcodeTemplateSchema = z.object({
id: z.int(), id: z.int(),
}); });
/**
* BaseMarketplaceSchema
*/
export const zBaseMarketplaceSchema = z.object({
id: z.int(),
name: z.string(),
iconUrl: z.string(),
});
/** /**
* BoardSchema * BoardSchema
*/ */
@ -377,6 +386,43 @@ export const zCreateDealServiceResponse = z.object({
entity: zDealServiceSchema, entity: zDealServiceSchema,
}); });
/**
* CreateMarketplaceSchema
*/
export const zCreateMarketplaceSchema = z.object({
baseMarketplace: zBaseMarketplaceSchema,
client: zClientSchema,
name: z.string(),
authData: z.object({}),
});
/**
* CreateMarketplaceRequest
*/
export const zCreateMarketplaceRequest = z.object({
entity: zCreateMarketplaceSchema,
});
/**
* MarketplaceSchema
*/
export const zMarketplaceSchema = z.object({
id: z.int(),
baseMarketplaceId: z.int(),
baseMarketplace: zBaseMarketplaceSchema,
client: zClientSchema,
name: z.string(),
authData: z.object({}),
});
/**
* CreateMarketplaceResponse
*/
export const zCreateMarketplaceResponse = z.object({
message: z.string(),
entity: zMarketplaceSchema,
});
/** /**
* CreateProductSchema * CreateProductSchema
*/ */
@ -650,6 +696,13 @@ export const zDeleteDealServiceResponse = z.object({
message: z.string(), message: z.string(),
}); });
/**
* DeleteMarketplaceResponse
*/
export const zDeleteMarketplaceResponse = z.object({
message: z.string(),
});
/** /**
* DeleteProductResponse * DeleteProductResponse
*/ */
@ -727,6 +780,13 @@ export const zGetBarcodeTemplatesResponse = z.object({
items: z.array(zBarcodeTemplateSchema), items: z.array(zBarcodeTemplateSchema),
}); });
/**
* GetBaseMarketplacesResponse
*/
export const zGetBaseMarketplacesResponse = z.object({
items: z.array(zBaseMarketplaceSchema),
});
/** /**
* GetBoardsResponse * GetBoardsResponse
*/ */
@ -771,6 +831,13 @@ export const zGetDealsResponse = z.object({
paginationInfo: zPaginationInfoSchema, paginationInfo: zPaginationInfoSchema,
}); });
/**
* GetMarketplacesResponse
*/
export const zGetMarketplacesResponse = z.object({
items: z.array(zMarketplaceSchema),
});
/** /**
* GetProductBarcodePdfRequest * GetProductBarcodePdfRequest
*/ */
@ -1037,6 +1104,30 @@ export const zUpdateDealServiceResponse = z.object({
message: z.string(), message: z.string(),
}); });
/**
* UpdateMarketplaceSchema
*/
export const zUpdateMarketplaceSchema = z.object({
baseMarketplace: z.optional(z.union([zBaseMarketplaceSchema, z.null()])),
client: z.optional(z.union([zClientSchema, z.null()])),
name: z.optional(z.union([z.string(), z.null()])),
authData: z.optional(z.union([z.object({}), z.null()])),
});
/**
* UpdateMarketplaceRequest
*/
export const zUpdateMarketplaceRequest = z.object({
entity: zUpdateMarketplaceSchema,
});
/**
* UpdateMarketplaceResponse
*/
export const zUpdateMarketplaceResponse = z.object({
message: z.string(),
});
/** /**
* UpdateProductSchema * UpdateProductSchema
*/ */
@ -1746,6 +1837,67 @@ export const zAddKitToDealData = z.object({
*/ */
export const zAddKitToDealResponse = zDealAddKitResponse; export const zAddKitToDealResponse = zDealAddKitResponse;
export const zGetBaseMarketplacesData = z.object({
body: z.optional(z.never()),
path: z.optional(z.never()),
query: z.optional(z.never()),
});
/**
* Successful Response
*/
export const zGetBaseMarketplacesResponse2 = zGetBaseMarketplacesResponse;
export const zGetMarketplacesData = z.object({
body: z.optional(z.never()),
path: z.object({
clientId: z.int(),
}),
query: z.optional(z.never()),
});
/**
* Successful Response
*/
export const zGetMarketplacesResponse2 = zGetMarketplacesResponse;
export const zCreateMarketplaceData = z.object({
body: zCreateMarketplaceRequest,
path: z.optional(z.never()),
query: z.optional(z.never()),
});
/**
* Successful Response
*/
export const zCreateMarketplaceResponse2 = zCreateMarketplaceResponse;
export const zDeleteMarketplaceData = z.object({
body: z.optional(z.never()),
path: z.object({
pk: z.int(),
}),
query: z.optional(z.never()),
});
/**
* Successful Response
*/
export const zDeleteMarketplaceResponse2 = zDeleteMarketplaceResponse;
export const zUpdateMarketplaceData = z.object({
body: zUpdateMarketplaceRequest,
path: z.object({
pk: z.int(),
}),
query: z.optional(z.never()),
});
/**
* Successful Response
*/
export const zUpdateMarketplaceResponse2 = zUpdateMarketplaceResponse;
export const zGetProductsData = z.object({ export const zGetProductsData = z.object({
body: z.optional(z.never()), body: z.optional(z.never()),
path: z.optional(z.never()), path: z.optional(z.never()),

View File

@ -1,4 +1,5 @@
import BarcodeTemplateEditorModal from "@/app/barcode-templates/modals/BarcodeTemplateFormModal/BarcodeTemplateEditorModal"; import BarcodeTemplateEditorModal from "@/app/barcode-templates/modals/BarcodeTemplateFormModal/BarcodeTemplateEditorModal";
import MarketplaceEditorModal from "@/app/clients/drawers/ClientMarketplacesDrawer/modals/MarketplaceEditorModal";
import ClientEditorModal from "@/app/clients/modals/ClientFormModal/ClientFormModal"; import ClientEditorModal from "@/app/clients/modals/ClientFormModal/ClientFormModal";
import ColorPickerModal from "@/app/deals/modals/ColorPickerModal/ColorPickerModal"; import ColorPickerModal from "@/app/deals/modals/ColorPickerModal/ColorPickerModal";
import DealsBoardFiltersModal from "@/app/deals/modals/DealsBoardFiltersModal/DealsBoardFiltersModal"; import DealsBoardFiltersModal from "@/app/deals/modals/DealsBoardFiltersModal/DealsBoardFiltersModal";
@ -38,4 +39,5 @@ export const modals = {
clientEditorModal: ClientEditorModal, clientEditorModal: ClientEditorModal,
printBarcodeModal: PrintBarcodeModal, printBarcodeModal: PrintBarcodeModal,
statusColorPickerModal: ColorPickerModal, statusColorPickerModal: ColorPickerModal,
marketplaceEditorModal: MarketplaceEditorModal,
}; };

View File

@ -11,7 +11,7 @@ import {
Textarea, Textarea,
TextInput, TextInput,
} from "@mantine/core"; } from "@mantine/core";
import { useClientsCrud } from "@/app/clients/hooks/useClientsCrud"; import { useClientsCrud } from "@/app/clients/hooks/cruds/useClientsCrud";
import FormFlexRow from "@/components/ui/FormFlexRow/FormFlexRow"; import FormFlexRow from "@/components/ui/FormFlexRow/FormFlexRow";
import useIsMobile from "@/hooks/utils/useIsMobile"; import useIsMobile from "@/hooks/utils/useIsMobile";
import { ClientSchema } from "@/lib/client"; import { ClientSchema } from "@/lib/client";

View File

@ -2,7 +2,7 @@
import { FC, useEffect, useMemo, useState } from "react"; import { FC, useEffect, useMemo, useState } from "react";
import { Text } from "@mantine/core"; import { Text } from "@mantine/core";
import useClientsList from "@/app/clients/hooks/useClientsList"; import useClientsList from "@/app/clients/hooks/lists/useClientsList";
import ObjectSelect, { import ObjectSelect, {
ObjectSelectProps, ObjectSelectProps,
} from "@/components/selects/ObjectSelect/ObjectSelect"; } from "@/components/selects/ObjectSelect/ObjectSelect";

View File

@ -0,0 +1,7 @@
enum BaseMarketplaceType {
WILDBERRIES = 1,
OZON,
YANDEX_MARKET,
}
export default BaseMarketplaceType;