-
+
Tour management system
-
+
A tour management system is software designed to organize and manage
tourism-related activities. It helps streamline trip planning,
booking, payment management, customer information, and travel
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/components/PaymentIcon.tsx b/frontend/plugins/tourism_ui/src/modules/tms/components/PaymentIcon.tsx
new file mode 100644
index 0000000000..af0c8428b0
--- /dev/null
+++ b/frontend/plugins/tourism_ui/src/modules/tms/components/PaymentIcon.tsx
@@ -0,0 +1,63 @@
+import React from 'react';
+import {
+ IconCreditCard,
+ IconCashBanknote,
+ IconBuilding,
+ IconPhone,
+ IconBrandVisa,
+ IconBrandMastercard,
+ IconFile,
+} from '@tabler/icons-react';
+
+export const paymentIconOptions = [
+ { value: 'visa', label: 'Visa' },
+ { value: 'mastercard', label: 'Mastercard' },
+ { value: 'cash', label: 'QPay' },
+ { value: 'bank', label: 'SocialPay' },
+ { value: 'credit-card', label: 'Credit Card' },
+ { value: 'mobile', label: 'Mobile Payment' },
+];
+
+interface PaymentIconProps {
+ iconType: string;
+ size?: number;
+ className?: string;
+}
+
+const PaymentIcon: React.FC = ({
+ iconType,
+ size = 16,
+ className = '',
+}) => {
+ const getIcon = () => {
+ switch (iconType) {
+ case 'credit-card':
+ return ;
+ case 'cash':
+ return ;
+ case 'bank':
+ return ;
+ case 'mobile':
+ return ;
+ case 'visa':
+ return (
+
+ );
+ case 'mastercard':
+ return (
+
+ );
+ case 'sign-alt':
+ return ;
+ default:
+ return ;
+ }
+ };
+
+ return getIcon();
+};
+
+export default PaymentIcon;
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/components/Preview.tsx b/frontend/plugins/tourism_ui/src/modules/tms/components/Preview.tsx
deleted file mode 100644
index 53d4896ef9..0000000000
--- a/frontend/plugins/tourism_ui/src/modules/tms/components/Preview.tsx
+++ /dev/null
@@ -1,217 +0,0 @@
-import {
- IconDeviceDesktop,
- IconDeviceMobile,
- IconDeviceTablet,
- IconWifi,
- IconAntennaBars5,
- IconBattery,
-} from '@tabler/icons-react';
-import { Button, Input } from 'erxes-ui';
-import { useState } from 'react';
-import { TmsFormType } from '@/tms/constants/formSchema';
-
-type DeviceType = 'desktop' | 'mobile' | 'tablet';
-
-interface PreviewProps {
- formData?: Partial;
-}
-
-export default function Preview({ formData }: PreviewProps) {
- const [activeDevice, setActiveDevice] = useState('desktop');
-
- const tourName = formData?.name || 'Таны тур оператор';
- const themeColor = formData?.color || '#4F46E5';
- const logoUrl =
- formData?.logo ||
- 'https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcTbvwVAC3F5xurW6mtfMrEoeWvuQpisg17tNg&s';
-
- const renderLoginForm = () => {
- return (
-
-
-
-
-
-
-
- Sign in to your account
-
-
- Enter your email and password below to access your account.
-
-
-
-
-
-
-
-
- Email
-
-
-
-
-
- Password
- Forgot password?
-
-
-
-
-
- Sign in
-
-
- );
- };
-
- const renderDeviceFrame = () => {
- switch (activeDevice) {
- case 'desktop':
- return (
-
-
-
-
- {renderLoginForm()}
-
-
-
- );
-
- case 'mobile':
- return (
-
- {/* Status bar */}
-
- {/* Notch */}
-
- {/* Content */}
-
-
-
- {renderLoginForm()}
-
-
-
- {/* Home indicator */}
-
-
- );
-
- case 'tablet':
- return (
-
- {/* Status bar */}
-
- {/* Content */}
-
- {/* Home button */}
-
-
- );
- }
- };
-
- return (
-
-
- {(['desktop', 'mobile', 'tablet'] as DeviceType[]).map((device) => (
-
setActiveDevice(device)}
- >
- {device === 'desktop' && (
-
- )}
- {device === 'mobile' && (
-
- )}
- {device === 'tablet' && (
-
- )}
-
- {device.charAt(0).toUpperCase() + device.slice(1)}
-
-
- ))}
-
-
-
- {renderDeviceFrame()}
-
-
- );
-}
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/components/TmsFormFields.tsx b/frontend/plugins/tourism_ui/src/modules/tms/components/TmsFormFields.tsx
index 2f01801ef1..cf43efb312 100644
--- a/frontend/plugins/tourism_ui/src/modules/tms/components/TmsFormFields.tsx
+++ b/frontend/plugins/tourism_ui/src/modules/tms/components/TmsFormFields.tsx
@@ -1,7 +1,10 @@
import { Control, useFieldArray } from 'react-hook-form';
-import { Button, Form, Input, Select, Upload } from 'erxes-ui';
+import { Button, Form, Input, Select, Upload, ColorPicker } from 'erxes-ui';
import { TmsFormType } from '@/tms/constants/formSchema';
-import { IconUpload, IconPlus, IconTrash } from '@tabler/icons-react';
+import { IconUpload, IconPlus, IconTrash, IconX } from '@tabler/icons-react';
+import PaymentIcon, { paymentIconOptions } from './PaymentIcon';
+import AddPaymentDialog from './AddPaymentDialog';
+import { SelectMember } from 'ui-modules';
export const TourName = ({ control }: { control: Control }) => {
return (
@@ -11,7 +14,7 @@ export const TourName = ({ control }: { control: Control }) => {
render={({ field }) => (
- Tour Name *
+ Name *
@@ -31,20 +34,17 @@ export const SelectColor = ({ control }: { control: Control }) => {
render={({ field }) => (
- Main color *
+ Main color *
-
-
-
+ {
+ field.onChange(value);
+ }}
+ className="w-24"
+ />
@@ -66,7 +66,6 @@ export const LogoField = ({ control }: { control: Control }) => {
{
if ('url' in fileInfo) {
@@ -74,28 +73,42 @@ export const LogoField = ({ control }: { control: Control }) => {
}
}}
>
-
-
-
-
-
- Upload logo
+ {field.value ? (
+
+
+
+
+
{
+ field.onChange('');
+ }}
+ >
+
-
-
- Max size: 15MB, File type: PNG
-
-
-
- {field.value && (
-
- )}
-
+
+ ) : (
+ <>
+
+
+
+
+ Upload logo
+
+
+ Max size: 15MB, File type: PNG
+
+
+ >
+ )}
@@ -130,29 +143,42 @@ export const FavIconField = ({
}
}}
>
-
-
-
-
-
-
- Upload favicon
+ {field.value ? (
+
+
+
+
+
{
+ field.onChange('');
+ }}
+ >
+
-
-
- Max size: 15MB, File type: PNG
-
-
-
- {field.value && (
-
- )}
-
+
+ ) : (
+ <>
+
+
+
+
+ Upload favicon
+
+
+ Max size: 15MB, File type: PNG
+
+
+ >
+ )}
@@ -161,14 +187,7 @@ export const FavIconField = ({
);
};
-const TestGeneralManager = [
- { label: 'Bold Bold', value: '1' },
- { label: 'Bat Bat', value: '2' },
- { label: 'Toroo Toroo', value: '3' },
- { label: 'Temuulen Temuulen', value: '4' },
-];
-
-export const GeneralManeger = ({
+export const GeneralManager = ({
control,
}: {
control: Control;
@@ -176,54 +195,22 @@ export const GeneralManeger = ({
return (
(
- General maneger
+ General Managers
- General maneger can be shown on the top of the post also in the list
+ General manager can be shown on the top of the post also in the list
view
- field.onChange([value])}
- value={field.value?.[0] || ''}
- >
-
-
-
- {'Choose team member'}
-
- }
- >
-
- {
- TestGeneralManager.find(
- (status) => status.value === field.value?.[0],
- )?.label
- }
-
-
-
-
-
-
- {TestGeneralManager.map((status) => (
-
- {status.label}
-
- ))}
-
-
-
+
+
+
+
+
)}
@@ -231,64 +218,25 @@ export const GeneralManeger = ({
);
};
-const TestManegers = [
- { label: 'Bold Bold', value: '1' },
- { label: 'Bat Bat', value: '2' },
- { label: 'Toroo Toroo', value: '3' },
- { label: 'Temuulen Temuulen', value: '4' },
-];
-
-export const Maneger = ({ control }: { control: Control }) => {
+export const Manager = ({ control }: { control: Control }) => {
return (
(
- Manegers
+ Managers
- Maneger can be shown on the top of the post also in the list view
+ Manager can be shown on the top of the post also in the list view
- field.onChange([value])}
- value={field.value?.[0] || ''}
- >
-
-
-
- {'Choose team member'}
-
- }
- >
-
- {
- TestManegers.find(
- (status) => status.value === field.value?.[0],
- )?.label
- }
-
-
-
-
-
-
- {TestManegers.map((status) => (
-
- {status.label}
-
- ))}
-
-
-
+
+
+
+
+
)}
@@ -313,53 +261,30 @@ export const Payments = ({ control }: { control: Control }) => {
Select payments that you want to use
-
-
-
field.onChange([value])}
- value={field.value?.[0] || ''}
- >
-
-
-
- {'Select payments'}
-
- }
- >
-
- {
- TestPayments.find(
- (status) => status.value === field.value?.[0],
- )?.label
- }
-
-
-
-
-
+
+
-
- {TestPayments.map((status) => (
-
- {status.label}
+
+
+
+
+ {TestPayments.map((payment) => (
+
+ {payment.label}
))}
-
-
-
+
+
+
-
-
- Add Payment
-
+
@@ -374,7 +299,7 @@ export const Token = ({ control }: { control: Control }) => {
control={control}
name="token"
render={({ field }) => (
-
+
Erxes app token
What is erxes app token ?
@@ -392,14 +317,6 @@ export const OtherPayments = ({
}: {
control: Control;
}) => {
- // Define Icon options
- const Icon = [
- { value: 'visa', label: 'Visa' },
- { value: 'mastercard', label: 'Mastercard' },
- { value: 'qpay', label: 'QPay' },
- { value: 'socialpay', label: 'SocialPay' },
- ];
-
const { fields, append, remove } = useFieldArray({
control,
name: 'otherPayments',
@@ -410,8 +327,8 @@ export const OtherPayments = ({
};
return (
-
-
+
+
Other Payments
@@ -425,10 +342,10 @@ export const OtherPayments = ({
-
+
@@ -440,9 +357,9 @@ export const OtherPayments = ({
{fields.map((field, index) => (
-
+
@@ -462,7 +379,7 @@ export const OtherPayments = ({
/>
-
+
@@ -482,7 +399,7 @@ export const OtherPayments = ({
/>
-
+
-
+
+ {field.value && (
+
+
+ {
+ paymentIconOptions.find(
+ (icon) => icon.value === field.value,
+ )?.label
+ }
+
+ )}
+
- {Icon.map((icon) => (
+ {paymentIconOptions.map((icon) => (
- {icon.label}
+
))}
@@ -517,7 +448,7 @@ export const OtherPayments = ({
/>
-
+
@@ -539,7 +470,7 @@ export const OtherPayments = ({
remove(index)}
>
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/components/TmsInformationFields.tsx b/frontend/plugins/tourism_ui/src/modules/tms/components/TmsInformationFields.tsx
index 04a0fde282..12bb7f6dd7 100644
--- a/frontend/plugins/tourism_ui/src/modules/tms/components/TmsInformationFields.tsx
+++ b/frontend/plugins/tourism_ui/src/modules/tms/components/TmsInformationFields.tsx
@@ -1,74 +1,92 @@
import { UseFormReturn } from 'react-hook-form';
-import { useState } from 'react';
+import { useAtom } from 'jotai';
+import { currentStepAtom } from '@/tms/states/tmsInformationFieldsAtoms';
import { TmsFormType } from '@/tms/constants/formSchema';
import {
TourName,
SelectColor,
LogoField,
FavIconField,
- GeneralManeger,
- Maneger,
+ GeneralManager,
+ Manager,
Payments,
Token,
OtherPayments,
} from '@/tms/components/TmsFormFields';
import { Button } from 'erxes-ui';
-import { IconPlus } from '@tabler/icons-react';
+import { useEffect } from 'react';
export const TmsInformationFields = ({
form,
onOpenChange,
onSubmit,
+ isOpen,
}: {
form: UseFormReturn;
onOpenChange?: (open: boolean) => void;
onSubmit?: (data: TmsFormType) => void;
+ isOpen?: boolean;
}) => {
- const [currentStep, setCurrentStep] = useState(1);
+ const [currentStep, setCurrentStep] = useAtom(currentStepAtom);
+
+ useEffect(() => {
+ if (isOpen) setCurrentStep(1);
+ }, [isOpen, setCurrentStep]);
const renderStepContent = () => {
- switch (currentStep) {
- case 1:
- return (
- <>
+ return (
+
+ {/* Step 1 */}
+
+
- >
- );
- case 2:
- return (
- <>
-
-
- Add team member
-
+
+
-
-
- >
- );
- case 3:
- return (
- <>
+ {/* Step 2 */}
+
+
+ {/* Step 3 */}
+
+
- >
- );
- default:
- return null;
- }
+
+
+
+ );
};
const handleNext = async () => {
if (currentStep === 1) {
- const result = await form.trigger(['name', 'color', 'logo']);
- if (result) setCurrentStep(2);
+ const result = await form.trigger(['name', 'color']);
+ if (result) {
+ setCurrentStep(2);
+ }
} else if (currentStep === 2) {
setCurrentStep(3);
}
@@ -83,7 +101,7 @@ export const TmsInformationFields = ({
}
function handleSave() {
- form.trigger(['payment', 'token']).then((isValid) => {
+ form.trigger(['payment', 'token', 'otherPayments']).then((isValid) => {
if (isValid && onSubmit) {
onSubmit(form.getValues());
}
@@ -91,64 +109,81 @@ export const TmsInformationFields = ({
}
return (
-
-
-
-
-
-
- STEP {currentStep}
-
-
-
- {currentStep === 1
- ? 'General information'
- : currentStep === 2
- ? 'Permission'
- : 'Payments'}
+
+
+
+
-
- {[1, 2, 3].map((step) => (
-
- ))}
-
-
+
{currentStep === 1
- ? 'Set up your TMS information'
+ ? 'General information'
: currentStep === 2
- ? 'Setup your permission'
- : 'Setup your payments'}
+ ? 'Permission'
+ : 'Payments'}
-
+
+ {[1, 2, 3].map((step) => (
+
+ ))}
+
+
+ {currentStep === 1
+ ? 'Set up your TMS information'
+ : currentStep === 2
+ ? 'Setup your permission'
+ : 'Setup your payments'}
+
+
+
-
+
{currentStep === 1 ? (
-
+
Cancel
) : (
-
+
Previous
)}
{currentStep < 3 ? (
- Next
+
+ Next
+
) : (
- Save
+
+ Save
+
)}
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/constants/formSchema.ts b/frontend/plugins/tourism_ui/src/modules/tms/constants/formSchema.ts
index 610bcba467..bb73fa704f 100644
--- a/frontend/plugins/tourism_ui/src/modules/tms/constants/formSchema.ts
+++ b/frontend/plugins/tourism_ui/src/modules/tms/constants/formSchema.ts
@@ -1,20 +1,20 @@
import { z } from 'zod';
export const TmsFormSchema = z.object({
- name: z.string().min(1, 'Tour name is required'),
+ name: z.string().min(1, 'Name is required'),
color: z.string().min(1, 'Color is required'),
logo: z.string().optional(),
favIcon: z.string().optional(),
- generalManeger: z.string().optional(),
- manegers: z.array(z.string()).optional(),
+ generalManager: z.array(z.string()).optional(),
+ managers: z.array(z.string()).optional(),
payment: z.string().optional(),
token: z.string().optional(),
otherPayments: z
.array(
z.object({
- type: z.string().optional(),
- title: z.string().optional(),
- icon: z.string().optional(),
+ type: z.string().min(1, 'Type is required'),
+ title: z.string().min(1, 'Title is required'),
+ icon: z.string().min(1, 'Icon is required'),
config: z.string().optional(),
}),
)
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/graphql/mutation.ts b/frontend/plugins/tourism_ui/src/modules/tms/graphql/mutation.ts
index c6c5ffb8b7..91efacb913 100644
--- a/frontend/plugins/tourism_ui/src/modules/tms/graphql/mutation.ts
+++ b/frontend/plugins/tourism_ui/src/modules/tms/graphql/mutation.ts
@@ -1,61 +1,67 @@
import { gql } from '@apollo/client';
-export const CREATE_BRANCH_BRANCH = gql`
- mutation bmsBranchAdd(
+export const CREATE_BRANCH = gql`
+ mutation BmsBranchAdd(
$name: String
$description: String
- $erxesAppToken: String
- $user1Ids: [String]
- $user2Ids: [String]
+ $generalManagerIds: [String]
+ $managerIds: [String]
$paymentIds: [String]
$paymentTypes: [JSON]
- $uiOptions: JSON
+ $departmentId: String
+ $token: String
+ $erxesAppToken: String
$permissionConfig: JSON
+ $uiOptions: JSON
) {
bmsBranchAdd(
name: $name
description: $description
- erxesAppToken: $erxesAppToken
- user1Ids: $user1Ids
- user2Ids: $user2Ids
+ generalManagerIds: $generalManagerIds
+ managerIds: $managerIds
paymentIds: $paymentIds
paymentTypes: $paymentTypes
- uiOptions: $uiOptions
+ departmentId: $departmentId
+ token: $token
+ erxesAppToken: $erxesAppToken
permissionConfig: $permissionConfig
+ uiOptions: $uiOptions
) {
_id
- name
- description
createdAt
- token
- erxesAppToken
- user1Ids
- user2Ids
- paymentIds
- paymentTypes
+ userId
user {
_id
+ username
+ email
details {
avatar
fullName
- __typename
+ shortName
}
- __typename
}
- uiOptions
+ name
+ description
+ generalManagerIds
+ managerIds
+ paymentIds
+ paymentTypes
+ departmentId
+ token
+ erxesAppToken
permissionConfig
- __typename
+ uiOptions
}
}
`;
-export const EDIT_BRANCH_LIST = gql`
+export const EDIT_BRANCH = gql`
mutation BmsBranchEdit(
$id: String
$name: String
$description: String
- $user1Ids: [String]
- $user2Ids: [String]
+ $generalManagerIds: [String]
+ $managerIds: [String]
$paymentIds: [String]
$paymentTypes: [JSON]
$departmentId: String
@@ -68,8 +74,8 @@ export const EDIT_BRANCH_LIST = gql`
_id: $id
name: $name
description: $description
- user1Ids: $user1Ids
- user2Ids: $user2Ids
+ generalManagerIds: $generalManagerIds
+ managerIds: $managerIds
paymentIds: $paymentIds
paymentTypes: $paymentTypes
departmentId: $departmentId
@@ -83,17 +89,18 @@ export const EDIT_BRANCH_LIST = gql`
userId
user {
_id
+ username
+ email
details {
avatar
fullName
- __typename
+ shortName
}
- __typename
}
name
description
- user1Ids
- user2Ids
+ generalManagerIds
+ managerIds
paymentIds
paymentTypes
departmentId
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/graphql/queries.ts b/frontend/plugins/tourism_ui/src/modules/tms/graphql/queries.ts
index 345e93a400..7dcd1ea165 100644
--- a/frontend/plugins/tourism_ui/src/modules/tms/graphql/queries.ts
+++ b/frontend/plugins/tourism_ui/src/modules/tms/graphql/queries.ts
@@ -1,32 +1,84 @@
import { gql } from '@apollo/client';
export const GET_BRANCH_LIST = gql`
- query bmsBranchList($sortField: String, $sortDirection: Int) {
- bmsBranchList(sortField: $sortField, sortDirection: $sortDirection) {
+ query BmsBranchList(
+ $limit: Int
+ $cursor: String
+ $cursorMode: CURSOR_MODE
+ $direction: CURSOR_DIRECTION
+ $orderBy: JSON
+ ) {
+ bmsBranchList(
+ limit: $limit
+ cursor: $cursor
+ cursorMode: $cursorMode
+ direction: $direction
+ orderBy: $orderBy
+ ) {
+ list {
+ _id
+ createdAt
+ userId
+ user {
+ _id
+ username
+ email
+ details {
+ avatar
+ fullName
+ shortName
+ }
+ }
+ name
+ description
+ generalManagerIds
+ managerIds
+ paymentIds
+ paymentTypes
+ departmentId
+ token
+ erxesAppToken
+ permissionConfig
+ uiOptions
+ }
+ totalCount
+ pageInfo {
+ hasNextPage
+ hasPreviousPage
+ startCursor
+ endCursor
+ }
+ }
+ }
+`;
+
+export const BRANCH_LIST_DETAIL = gql`
+ query BmsBranchDetail($id: String!) {
+ bmsBranchDetail(_id: $id) {
_id
- name
- description
createdAt
- token
- erxesAppToken
- user1Ids
- user2Ids
- paymentIds
- paymentTypes
+ userId
user {
_id
+ username
+ email
details {
avatar
fullName
- __typename
+ shortName
}
- __typename
}
- uiOptions
+ name
+ description
+ generalManagerIds
+ managerIds
+ paymentIds
+ paymentTypes
+ departmentId
+ token
+ erxesAppToken
permissionConfig
- __typename
+ uiOptions
}
}
`;
-
-
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchDetail.ts b/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchDetail.ts
new file mode 100644
index 0000000000..3d0571c746
--- /dev/null
+++ b/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchDetail.ts
@@ -0,0 +1,26 @@
+import { useQuery } from '@apollo/client';
+import { BRANCH_LIST_DETAIL } from '../graphql/queries';
+import { IBranch } from '../types/branch';
+
+interface BranchDetailResponse {
+ bmsBranchDetail: IBranch;
+}
+
+interface BranchDetailVariables {
+ id: string;
+}
+
+export const useBranchDetail = (variables: BranchDetailVariables) => {
+ const { data, loading, error } = useQuery<
+ BranchDetailResponse,
+ BranchDetailVariables
+ >(BRANCH_LIST_DETAIL, {
+ variables,
+ skip: !variables.id,
+ fetchPolicy: 'cache-and-network',
+ });
+
+ const branchDetail = data?.bmsBranchDetail;
+
+ return { branchDetail, loading, error };
+};
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchDuplicate.ts b/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchDuplicate.ts
new file mode 100644
index 0000000000..47993a2ced
--- /dev/null
+++ b/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchDuplicate.ts
@@ -0,0 +1,67 @@
+import { useMutation } from '@apollo/client';
+import { CREATE_BRANCH } from '../graphql/mutation';
+import { GET_BRANCH_LIST } from '../graphql/queries';
+import { IBranch } from '../types/branch';
+
+interface DuplicateBranchResponse {
+ bmsBranchAdd: IBranch;
+}
+
+interface IPaymentType {
+ id: string;
+ name: string;
+}
+
+interface IPermissionConfig {
+ permission: string;
+ enabled: boolean;
+}
+
+export interface IDuplicateBranchVariables {
+ name: string;
+ description?: string;
+ generalManagerIds?: string[];
+ managerIds?: string[];
+ paymentIds?: string[];
+ paymentTypes?: IPaymentType[];
+ departmentId?: string;
+ token?: string;
+ erxesAppToken?: string;
+ permissionConfig?: IPermissionConfig[];
+ uiOptions?: {
+ logo?: string;
+ favIcon?: string;
+ colors?: {
+ primary?: string;
+ };
+ };
+}
+
+export const useBranchDuplicate = () => {
+ const [duplicateBranchMutation, { loading, error }] = useMutation<
+ DuplicateBranchResponse,
+ IDuplicateBranchVariables
+ >(CREATE_BRANCH, {
+ refetchQueries: [
+ {
+ query: GET_BRANCH_LIST,
+ variables: {
+ limit: 10,
+ },
+ },
+ ],
+ onError: (error) => {
+ console.error('Error duplicating branch:', error);
+ },
+ });
+
+ const duplicateBranch = (options: {
+ variables: IDuplicateBranchVariables;
+ onCompleted?: (data: DuplicateBranchResponse) => void;
+ onError?: (error: any) => void;
+ }) => {
+ return duplicateBranchMutation(options);
+ };
+
+ return { duplicateBranch, loading, error };
+};
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchEdit.ts b/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchEdit.ts
index 26a4e82332..7b7318fcb7 100644
--- a/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchEdit.ts
+++ b/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchEdit.ts
@@ -1,16 +1,63 @@
-import { useQuery } from '@apollo/client';
-import { EDIT_BRANCH_LIST } from '../graphql/mutation';
+import { useMutation } from '@apollo/client';
+import { EDIT_BRANCH } from '../graphql/mutation';
+import { GET_BRANCH_LIST } from '../graphql/queries';
import { IBranch } from '../types/branch';
-interface BranchListResponse {
- bmsBranchList: IBranch[];
+interface EditBranchResponse {
+ bmsBranchEdit: IBranch;
+}
+
+export interface IEditBranchVariables {
+ id: string;
+ name?: string;
+ description?: string;
+ generalManagerIds?: string[];
+ managerIds?: string[];
+ paymentIds?: string[];
+ paymentTypes?: any[];
+ departmentId?: string;
+ token?: string;
+ erxesAppToken?: string;
+ permissionConfig?: any[];
+ uiOptions?: {
+ logo?: string;
+ favIcon?: string;
+ colors?: {
+ primary?: string;
+ };
+ };
}
export const useBranchEdit = () => {
- const { data, loading, error } =
- useQuery
(EDIT_BRANCH_LIST);
+ const [editBranchMutation, { loading, error }] = useMutation<
+ EditBranchResponse,
+ IEditBranchVariables
+ >(EDIT_BRANCH, {
+ refetchQueries: [
+ {
+ query: GET_BRANCH_LIST,
+ variables: {
+ limit: 10,
+ },
+ },
+ ],
+ onError: (error) => {
+ // Replace with proper error logging service
+ console.error('Branch edit failed:', error);
+ },
+ });
- const list = data?.bmsBranchList || [];
+ const editBranch = (options: {
+ variables: IEditBranchVariables;
+ onCompleted?: (data: EditBranchResponse) => void;
+ onError?: (error: any) => void;
+ }) => {
+ return editBranchMutation(options);
+ };
- return { list, loading, error };
+ return {
+ editBranch,
+ loading,
+ error,
+ };
};
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchList.ts b/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchList.ts
index fc48398103..f431d37b28 100644
--- a/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchList.ts
+++ b/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchList.ts
@@ -2,15 +2,35 @@ import { useQuery } from '@apollo/client';
import { GET_BRANCH_LIST } from '../graphql/queries';
import { IBranch } from '../types/branch';
+interface PageInfo {
+ hasNextPage: boolean;
+ hasPreviousPage: boolean;
+ startCursor: string;
+ endCursor: string;
+}
+
interface BranchListResponse {
- bmsBranchList: IBranch[];
+ bmsBranchList: {
+ list: IBranch[];
+ totalCount: number;
+ pageInfo: PageInfo;
+ };
}
-export const useBranchList = () => {
- const { data, loading, error } =
- useQuery(GET_BRANCH_LIST);
+export const useBranchList = (limit = 10) => {
+ const { data, loading, error, refetch } = useQuery(
+ GET_BRANCH_LIST,
+ {
+ variables: {
+ limit,
+ },
+ fetchPolicy: 'network-only',
+ },
+ );
- const list = data?.bmsBranchList || [];
+ const list = data?.bmsBranchList?.list || [];
+ const totalCount = data?.bmsBranchList?.totalCount || 0;
+ const pageInfo = data?.bmsBranchList?.pageInfo;
- return { list, loading, error };
+ return { list, totalCount, pageInfo, loading, error, refetch };
};
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchRemove.ts b/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchRemove.ts
index ec4fd4f8af..a19b6ccbb2 100644
--- a/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchRemove.ts
+++ b/frontend/plugins/tourism_ui/src/modules/tms/hooks/BranchRemove.ts
@@ -4,11 +4,18 @@ import { GET_BRANCH_LIST } from '../graphql/queries';
import { IBranchRemoveResponse, IBranchRemoveVariables } from '../types/branch';
export const useBranchRemove = () => {
- const [removeBranch, { loading, error }] = useMutation<
+ const [removeBranch, { loading }] = useMutation<
IBranchRemoveResponse,
IBranchRemoveVariables
>(REMOVE_BRANCH, {
- refetchQueries: [{ query: GET_BRANCH_LIST }],
+ refetchQueries: [
+ {
+ query: GET_BRANCH_LIST,
+ variables: {
+ limit: 10,
+ },
+ },
+ ],
onError: (error) => {
console.error('Error removing branch:', error);
},
@@ -21,10 +28,10 @@ export const useBranchRemove = () => {
});
return response.data?.bmsBranchRemove || false;
- } catch (error) {
+ } catch {
return false;
}
};
- return { removeBranchById, loading, error };
+ return { removeBranchById, loading };
};
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/hooks/CreateBranch.ts b/frontend/plugins/tourism_ui/src/modules/tms/hooks/CreateBranch.ts
index 90ab79863f..461663a539 100644
--- a/frontend/plugins/tourism_ui/src/modules/tms/hooks/CreateBranch.ts
+++ b/frontend/plugins/tourism_ui/src/modules/tms/hooks/CreateBranch.ts
@@ -1,5 +1,6 @@
import { useMutation } from '@apollo/client';
-import { CREATE_BRANCH_BRANCH } from '../graphql/mutation';
+import { CREATE_BRANCH } from '../graphql/mutation';
+import { GET_BRANCH_LIST } from '../graphql/queries';
import { IBranch } from '../types/branch';
interface CreateBranchResponse {
@@ -9,22 +10,42 @@ interface CreateBranchResponse {
export interface ICreateBranchVariables {
name: string;
description?: string;
- user1Ids?: string[];
- user2Ids?: string[];
+ generalManagerIds?: string[];
+ managerIds?: string[];
paymentIds?: string[];
- paymentTypes?: any[];
departmentId?: string;
token?: string;
erxesAppToken?: string;
- permissionConfig?: any;
- uiOptions?: any;
+ permissionConfig?: {
+ _id?: string;
+ type: string;
+ title: string;
+ icon: string;
+ config?: string;
+ }[];
+ uiOptions?: {
+ logo?: string;
+ favIcon?: string;
+ colors?: {
+ primary?: string;
+ };
+ };
}
export const useCreateBranch = () => {
const [createBranchMutation, { loading, error }] = useMutation<
CreateBranchResponse,
ICreateBranchVariables
- >(CREATE_BRANCH_BRANCH);
+ >(CREATE_BRANCH, {
+ refetchQueries: [
+ {
+ query: GET_BRANCH_LIST,
+ variables: {
+ limit: 10,
+ },
+ },
+ ],
+ });
const createBranch = (options: {
variables: ICreateBranchVariables;
@@ -34,5 +55,9 @@ export const useCreateBranch = () => {
return createBranchMutation(options);
};
- return { createBranch, loading, error };
+ return {
+ createBranch,
+ loading,
+ error,
+ };
};
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/states/tmsInformationFieldsAtoms.ts b/frontend/plugins/tourism_ui/src/modules/tms/states/tmsInformationFieldsAtoms.ts
new file mode 100644
index 0000000000..d236ab84c2
--- /dev/null
+++ b/frontend/plugins/tourism_ui/src/modules/tms/states/tmsInformationFieldsAtoms.ts
@@ -0,0 +1,4 @@
+import { atom } from 'jotai';
+
+export const currentStepAtom = atom(1);
+
diff --git a/frontend/plugins/tourism_ui/src/modules/tms/types/branch.ts b/frontend/plugins/tourism_ui/src/modules/tms/types/branch.ts
index fa7478ffb6..0e69e32d44 100644
--- a/frontend/plugins/tourism_ui/src/modules/tms/types/branch.ts
+++ b/frontend/plugins/tourism_ui/src/modules/tms/types/branch.ts
@@ -17,6 +17,8 @@ export interface IBranch {
erxesAppToken: string;
user1Ids: string[];
user2Ids: string[];
+ generalManagerIds: string[];
+ managerIds: string[];
paymentIds: string[];
paymentTypes: string[];
user: IBranchUser;
diff --git a/frontend/plugins/tourism_ui/src/pages/pms/IndexPage.tsx b/frontend/plugins/tourism_ui/src/pages/pms/IndexPage.tsx
index 7458494e81..e2f2857cfb 100644
--- a/frontend/plugins/tourism_ui/src/pages/pms/IndexPage.tsx
+++ b/frontend/plugins/tourism_ui/src/pages/pms/IndexPage.tsx
@@ -2,7 +2,8 @@ import { IconBox, IconSettings } from '@tabler/icons-react';
import { Breadcrumb, Button, Separator } from 'erxes-ui';
import { PageHeader } from 'ui-modules';
import { Link } from 'react-router-dom';
-import { PmsCreateSheet } from '@/pms/components/CreatePmsSheet';
+import { PmsCreateSheet } from '~/modules/pms/components/pmsSheet/CreatePmsSheet';
+import PmsBranchList from '~/modules/pms/components/pmsBranchList';
export const IndexPage = () => {
return (
@@ -34,6 +35,8 @@ export const IndexPage = () => {
+
+
);
};
diff --git a/frontend/plugins/tourism_ui/src/pages/tms/IndexPage.tsx b/frontend/plugins/tourism_ui/src/pages/tms/IndexPage.tsx
index 963c4d6c7a..92588b9592 100644
--- a/frontend/plugins/tourism_ui/src/pages/tms/IndexPage.tsx
+++ b/frontend/plugins/tourism_ui/src/pages/tms/IndexPage.tsx
@@ -2,7 +2,7 @@ import { IconBox, IconSettings } from '@tabler/icons-react';
import { Breadcrumb, Button, Separator } from 'erxes-ui';
import { PageHeader } from 'ui-modules';
import { Link } from 'react-router-dom';
-import { TmsCreateSheet } from '@/tms/components/CreateTmsSheet';
+import { TmsCreateSheet } from '~/modules/tms/components/CreateTmsSheet';
import { BranchList } from '@/tms/components/BranchList';
export const IndexPage = () => {
diff --git a/frontend/plugins/tourism_ui/src/pages/tms/PreviewPage.tsx b/frontend/plugins/tourism_ui/src/pages/tms/PreviewPage.tsx
new file mode 100644
index 0000000000..468c76866a
--- /dev/null
+++ b/frontend/plugins/tourism_ui/src/pages/tms/PreviewPage.tsx
@@ -0,0 +1,103 @@
+import { readImage } from 'erxes-ui/utils/core';
+import { useEffect, useState } from 'react';
+import { Input, Select } from 'erxes-ui';
+
+const PreviewPage = () => {
+ const [urlParams, setUrlParams] = useState
(null);
+
+ useEffect(() => {
+ if (typeof window !== 'undefined') {
+ setUrlParams(new URLSearchParams(window.location.search));
+ }
+ }, []);
+
+ const tourName = urlParams?.get('name') || 'Таны тур оператор';
+ const themeColor = urlParams?.get('color') || '#4F46E5';
+ const logoParam = urlParams?.get('logo');
+ const logoUrl = logoParam
+ ? readImage(logoParam)
+ : 'https://placehold.co/150x150';
+
+ return (
+
+
+
+
+
+ (e.currentTarget.src = 'https://placehold.co/150x150')
+ }
+ />
+
+
+ Sign in to your account
+
+
+ Enter your email and password below to access your account.
+
+
+
+
+
+ );
+};
+
+export default PreviewPage;