@syzy/apphost 1.0.1 → 1.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/App.js +83 -0
- package/dist/AppHostProvider.js +4 -0
- package/dist/AppHostRoutes.js +7 -0
- package/dist/api/image-api.js +45 -0
- package/dist/api/mapping-api.js +427 -0
- package/dist/bookingModule/components/AmenityForm.js +19 -0
- package/dist/bookingModule/components/BillingManagement.js +17 -0
- package/dist/bookingModule/components/CreateRoomForm.js +19 -0
- package/dist/bookingModule/components/ExtraRequirementForm.js +19 -0
- package/dist/bookingModule/components/ReservationForm.js +18 -0
- package/dist/bookingModule/components/RoomCategoryForm.js +19 -0
- package/dist/bookingModule/components/RoomCategoryPriceForm.js +20 -0
- package/dist/bookingModule/components/RoomExtraRequirementCapture.js +18 -0
- package/dist/bookingModule/components/RoomFacilityForm.js +19 -0
- package/dist/bookingModule/components/RoomReservationAction.js +18 -0
- package/dist/components/Home/Home.js +14 -0
- package/dist/components/Loader/Loader.js +5 -0
- package/dist/components/Login/Login.js +149 -0
- package/dist/components/Login/loginSchema.js +41 -0
- package/dist/components/Mappings/BranchMapping/Branch.js +135 -0
- package/dist/components/Mappings/BranchMapping/BranchTableColumns.js +21 -0
- package/dist/components/Mappings/BranchMapping/MappingFormBranchUser.js +150 -0
- package/dist/components/Mappings/BranchMapping/MappingTableColumns.js +29 -0
- package/dist/components/Mappings/BranchMapping/branchSchema.js +34 -0
- package/dist/components/Mappings/ComponentMapping/ComponentRoleMapping.js +98 -0
- package/dist/components/Mappings/ComponentMapping/componentRoleColumns.js +29 -0
- package/dist/components/Mappings/MappingForm/MappingForm.js +142 -0
- package/dist/components/Mappings/MappingForm/mappingSchema.js +32 -0
- package/dist/components/Mappings/RoleMapping/MappingFormUserRole.js +194 -0
- package/dist/components/Mappings/RoleMapping/UserRoleTableColumns.js +33 -0
- package/dist/components/NavBar/Sidebar.js +56 -0
- package/dist/components/ProfileForm/ProfileForm.js +190 -0
- package/dist/components/ProfileForm/ProfileList.js +33 -0
- package/dist/components/ProfileForm/profileColumns.js +67 -0
- package/dist/components/ProfileForm/profileSchema.js +50 -0
- package/dist/components/SettingsPage/SettingsPage.js +240 -0
- package/dist/components/api/settings-api.js +131 -0
- package/dist/components/common/Form/FormActionButtons.js +6 -0
- package/dist/components/common/Form/FormLabel.js +6 -0
- package/dist/components/common/ListTable/ListHeader.js +5 -0
- package/dist/components/common/ListTable/ListTable.js +31 -0
- package/dist/components/common/Modal/Modal.js +6 -0
- package/dist/config/EnvConfig.js +13 -0
- package/dist/config/amplifyConfig.js +45 -0
- package/dist/configureAppHost.js +5 -0
- package/dist/customGraphQL/customMutations.js +53 -0
- package/dist/customGraphQL/customQueries.js +104 -0
- package/dist/domain/input/input-types.js +1 -0
- package/dist/domain/model/BranchDto.js +8 -0
- package/dist/domain/model/ComponentMappingDto.js +19 -0
- package/dist/domain/model/MappingDto.js +16 -0
- package/dist/domain/model/PrefixDescriptionDto.js +13 -0
- package/dist/domain/model/ProfileDto.js +20 -0
- package/dist/domain/model/RoleMappingDto.js +19 -0
- package/dist/domain/model/SettingsDto.js +7 -0
- package/dist/domain/model/UserMappingDto.js +28 -0
- package/dist/domain/model/imageDto.js +1 -0
- package/dist/domain/type/EntityTypes.js +6 -0
- package/dist/domain/type/MappingOptions.js +1 -0
- package/dist/domain/type/MappingTypes.js +7 -0
- package/dist/domain/type/Nullable.js +1 -0
- package/dist/domain/type/ResettingPeriodOptions.js +8 -0
- package/dist/domain/type/RolesEnum.js +7 -0
- package/dist/domain/type/SelectType.js +1 -0
- package/dist/domain/type/StatusEnum.js +6 -0
- package/dist/domain/type/signUpOptions.js +4 -0
- package/dist/domain/type/statusOptions.js +4 -0
- package/dist/graphql/profileQueries.js +89 -0
- package/dist/hoc/withSyzyAuth.js +87 -0
- package/dist/hooks/useCurrentUser.js +6 -0
- package/dist/hooks/useDispatch.js +7 -0
- package/dist/hooks/usePermission.js +7 -0
- package/dist/index.js +3 -15
- package/dist/main.js +60 -0
- package/dist/services/Client.Service.js +96 -0
- package/dist/services/Storage-service.js +26 -0
- package/dist/services/navigationMenu.js +9 -0
- package/dist/static/constants.js +34 -0
- package/dist/store/AppAction.js +5 -0
- package/dist/store/AppContext.js +3 -0
- package/dist/store/AppContextType.js +6 -0
- package/dist/store/AppProvider.js +32 -0
- package/dist/store/HostedInContainerContext.js +11 -0
- package/dist/store/SesssionReducer.js +16 -0
- package/dist/types/App.d.ts +4 -0
- package/dist/types/AppHostProvider.d.ts +6 -0
- package/dist/types/AppHostRoutes.d.ts +1 -0
- package/dist/types/api/image-api.d.ts +8 -0
- package/dist/types/api/mapping-api.d.ts +80 -0
- package/dist/types/bookingModule/components/AmenityForm.d.ts +3 -0
- package/dist/types/bookingModule/components/BillingManagement.d.ts +3 -0
- package/dist/types/bookingModule/components/CreateRoomForm.d.ts +3 -0
- package/dist/types/bookingModule/components/ExtraRequirementForm.d.ts +3 -0
- package/dist/types/bookingModule/components/ReservationForm.d.ts +3 -0
- package/dist/types/bookingModule/components/RoomCategoryForm.d.ts +3 -0
- package/dist/types/bookingModule/components/RoomCategoryPriceForm.d.ts +3 -0
- package/dist/types/bookingModule/components/RoomExtraRequirementCapture.d.ts +3 -0
- package/dist/types/bookingModule/components/RoomFacilityForm.d.ts +3 -0
- package/dist/types/bookingModule/components/RoomReservationAction.d.ts +3 -0
- package/dist/types/components/Home/Home.d.ts +3 -0
- package/dist/types/components/Loader/Loader.d.ts +2 -0
- package/dist/types/components/Login/Login.d.ts +7 -0
- package/dist/types/components/Login/loginSchema.d.ts +27 -0
- package/dist/types/components/Mappings/BranchMapping/Branch.d.ts +5 -0
- package/dist/types/components/Mappings/BranchMapping/BranchTableColumns.d.ts +10 -0
- package/dist/types/components/Mappings/BranchMapping/MappingFormBranchUser.d.ts +3 -0
- package/dist/types/components/Mappings/BranchMapping/MappingTableColumns.d.ts +14 -0
- package/dist/types/components/Mappings/BranchMapping/branchSchema.d.ts +37 -0
- package/dist/types/components/Mappings/ComponentMapping/ComponentRoleMapping.d.ts +3 -0
- package/dist/types/components/Mappings/ComponentMapping/componentRoleColumns.d.ts +3 -0
- package/dist/types/components/Mappings/MappingForm/MappingForm.d.ts +35 -0
- package/dist/types/components/Mappings/MappingForm/mappingSchema.d.ts +23 -0
- package/dist/types/components/Mappings/RoleMapping/MappingFormUserRole.d.ts +5 -0
- package/dist/types/components/Mappings/RoleMapping/UserRoleTableColumns.d.ts +3 -0
- package/dist/types/components/NavBar/Sidebar.d.ts +4 -0
- package/dist/types/components/ProfileForm/ProfileForm.d.ts +3 -0
- package/dist/types/components/ProfileForm/ProfileList.d.ts +3 -0
- package/dist/types/components/ProfileForm/profileColumns.d.ts +3 -0
- package/dist/types/components/ProfileForm/profileSchema.d.ts +52 -0
- package/dist/types/components/SettingsPage/SettingsPage.d.ts +3 -0
- package/dist/types/components/api/settings-api.d.ts +26 -0
- package/dist/types/components/common/Form/FormActionButtons.d.ts +11 -0
- package/dist/types/components/common/Form/FormLabel.d.ts +8 -0
- package/dist/types/components/common/ListTable/ListHeader.d.ts +8 -0
- package/dist/types/components/common/ListTable/ListTable.d.ts +17 -0
- package/dist/types/components/common/Modal/Modal.d.ts +11 -0
- package/dist/types/config/EnvConfig.d.ts +13 -0
- package/dist/types/config/amplifyConfig.d.ts +1 -0
- package/dist/types/configureAppHost.d.ts +6 -0
- package/dist/types/customGraphQL/customMutations.d.ts +3 -0
- package/dist/types/customGraphQL/customQueries.d.ts +7 -0
- package/dist/types/domain/input/input-types.d.ts +47 -0
- package/dist/types/domain/model/BranchDto.d.ts +9 -0
- package/dist/types/domain/model/ComponentMappingDto.d.ts +24 -0
- package/dist/types/domain/model/MappingDto.d.ts +30 -0
- package/dist/types/domain/model/PrefixDescriptionDto.d.ts +16 -0
- package/dist/types/domain/model/ProfileDto.d.ts +21 -0
- package/dist/types/domain/model/RoleMappingDto.d.ts +14 -0
- package/dist/types/domain/model/SettingsDto.d.ts +8 -0
- package/dist/types/domain/model/UserMappingDto.d.ts +14 -0
- package/dist/types/domain/model/imageDto.d.ts +4 -0
- package/dist/types/domain/type/EntityTypes.d.ts +5 -0
- package/dist/types/domain/type/MappingOptions.d.ts +5 -0
- package/dist/types/domain/type/MappingTypes.d.ts +6 -0
- package/dist/types/domain/type/Nullable.d.ts +13 -0
- package/dist/types/domain/type/ResettingPeriodOptions.d.ts +2 -0
- package/dist/types/domain/type/RolesEnum.d.ts +6 -0
- package/dist/types/domain/type/SelectType.d.ts +16 -0
- package/dist/types/domain/type/StatusEnum.d.ts +5 -0
- package/dist/types/domain/type/signUpOptions.d.ts +2 -0
- package/dist/types/domain/type/statusOptions.d.ts +2 -0
- package/dist/types/graphql/profileQueries.d.ts +4 -0
- package/dist/types/hoc/withSyzyAuth.d.ts +2 -0
- package/dist/types/hooks/useCurrentUser.d.ts +3 -0
- package/dist/types/hooks/useDispatch.d.ts +3 -0
- package/dist/types/hooks/usePermission.d.ts +1 -0
- package/dist/types/index.d.ts +3 -0
- package/dist/types/main.d.ts +4 -0
- package/dist/types/services/Client.Service.d.ts +12 -0
- package/dist/types/services/Storage-service.d.ts +2 -0
- package/dist/types/services/navigationMenu.d.ts +1 -0
- package/dist/types/static/constants.d.ts +34 -0
- package/dist/types/store/AppAction.d.ts +11 -0
- package/dist/types/store/AppContext.d.ts +3 -0
- package/dist/types/store/AppContextType.d.ts +12 -0
- package/dist/types/store/AppProvider.d.ts +7 -0
- package/dist/types/store/HostedInContainerContext.d.ts +5 -0
- package/dist/types/store/SesssionReducer.d.ts +4 -0
- package/dist/types/types.d.ts +26 -0
- package/dist/types/util/AuthUtils.d.ts +1 -0
- package/dist/types/util/LogEnum.d.ts +6 -0
- package/dist/types/util/Logger.d.ts +6 -0
- package/dist/types/util/SyzyDate.d.ts +69 -0
- package/dist/types/util/dateUtils.d.ts +10 -0
- package/dist/types/util/hostedinContainer.d.ts +1 -0
- package/dist/types/util/model-types.d.ts +96 -0
- package/dist/types/util/prefixAndResettingValidation.d.ts +9 -0
- package/dist/types/util/transformToData.d.ts +1 -0
- package/dist/types.js +14 -0
- package/dist/util/AuthUtils.js +10 -0
- package/dist/util/LogEnum.js +7 -0
- package/dist/util/Logger.js +18 -0
- package/dist/util/SyzyDate.js +265 -0
- package/dist/util/dateUtils.js +24 -0
- package/dist/util/hostedinContainer.js +9 -0
- package/dist/util/model-types.js +18 -0
- package/dist/util/prefixAndResettingValidation.js +54 -0
- package/dist/util/transformToData.js +9 -0
- package/package.json +14 -9
- package/dist/__federation_shared_@tanstack/react-query-DHuUsaNz.js +0 -2517
- package/dist/__federation_shared_react-CikWE6qG.js +0 -7
- package/dist/__federation_shared_react-bootstrap-BKlZRvMR.js +0 -7516
- package/dist/__federation_shared_react-dom-vrQ70Ay8.js +0 -372
- package/dist/__federation_shared_react-router-dom-BKminmS4.js +0 -10448
- package/dist/__federation_shared_react-select-B6kehBDI.js +0 -4056
- package/dist/__federation_shared_react-toastify-B0S0UGr3.js +0 -412
- package/dist/_commonjsHelpers-C6fGbg64.js +0 -6
- package/dist/_virtual___federation_fn_import-XZCKozko.js +0 -217
- package/dist/favicon.ico +0 -0
- package/dist/index-DgtWMtjZ.js +0 -184
- package/dist/index-eZknuYwc.js +0 -1219
- package/dist/jsx-runtime-D_t4bG-_.js +0 -264
- package/dist/manifest.webmanifest +0 -1
- package/dist/pwa/Hotel-icon.jpg +0 -0
- package/dist/pwa/apple-touch-icon-180x180.png +0 -0
- package/dist/pwa/favicon.ico +0 -0
- package/dist/pwa/maskable-icon-512x512.png +0 -0
- package/dist/pwa/pwa-192x192.png +0 -0
- package/dist/pwa/pwa-512x512.png +0 -0
- package/dist/pwa/pwa-64x64.png +0 -0
- package/dist/registerSW.js +0 -1
- package/dist/sw.js +0 -1
- package/dist/workbox-1ef09536.js +0 -1
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import React, { Suspense, useContext } from 'react';
|
|
3
|
+
import AppContext from '../../store/AppContext';
|
|
4
|
+
const RemoteRoomCategoryForm = React.lazy(() => import("bookingUIApp/RoomCategoryForm"));
|
|
5
|
+
const RoomCategoryForm = () => {
|
|
6
|
+
const { user } = useContext(AppContext) ?? { user: undefined };
|
|
7
|
+
const rawBranch = user?.branchId ?? "";
|
|
8
|
+
const parts = rawBranch.split("#");
|
|
9
|
+
const branchId = parts[1];
|
|
10
|
+
const isSuperAdmin = user?.roles?.includes("SUPERADMIN") ?? false;
|
|
11
|
+
return (_jsx("div", { children: _jsx(Suspense, { children: _jsx(RemoteRoomCategoryForm, { branchId: branchId, isSuperAdmin: isSuperAdmin, classNames: {
|
|
12
|
+
fontTitle: "font-title",
|
|
13
|
+
fontLabel: "font-label",
|
|
14
|
+
formGroup: "form-group",
|
|
15
|
+
buttonPrimary: "btn-primary-global",
|
|
16
|
+
buttonSecondary: "btn-secondary-global"
|
|
17
|
+
} }) }) }));
|
|
18
|
+
};
|
|
19
|
+
export default RoomCategoryForm;
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import React, { Suspense, useContext } from 'react';
|
|
3
|
+
import AppContext from '../../store/AppContext';
|
|
4
|
+
const RemoteRoomCategoryPriceForm = React.lazy(() => import("bookingUIApp/RoomCategoryPriceForm"));
|
|
5
|
+
const RoomCategoryPriceForm = () => {
|
|
6
|
+
const { user } = useContext(AppContext) ?? { user: undefined };
|
|
7
|
+
const rawBranch = user?.branchId ?? "";
|
|
8
|
+
const parts = rawBranch.split("#");
|
|
9
|
+
const branchId = parts[1];
|
|
10
|
+
const userId = `${parts[3]}#${parts[4]}`;
|
|
11
|
+
const isSuperAdmin = user?.roles?.includes("SUPERADMIN") ?? false;
|
|
12
|
+
return (_jsx("div", { children: _jsx(Suspense, { children: _jsx(RemoteRoomCategoryPriceForm, { branchId: branchId, isSuperAdmin: isSuperAdmin, userId: userId, classNames: {
|
|
13
|
+
fontTitle: "font-title",
|
|
14
|
+
fontLabel: "font-label",
|
|
15
|
+
formGroup: "form-group",
|
|
16
|
+
buttonPrimary: "btn-primary-global",
|
|
17
|
+
buttonSecondary: "btn-secondary-global"
|
|
18
|
+
} }) }) }));
|
|
19
|
+
};
|
|
20
|
+
export default RoomCategoryPriceForm;
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import React, { Suspense, useContext } from 'react';
|
|
3
|
+
import AppContext from '../../store/AppContext';
|
|
4
|
+
const RemoteRoomList = React.lazy(() => import("bookingUIApp/RoomList"));
|
|
5
|
+
const RoomExtraRequirementCapture = () => {
|
|
6
|
+
const { user } = useContext(AppContext) ?? { user: undefined };
|
|
7
|
+
const rawBranch = user?.branchId ?? "";
|
|
8
|
+
const parts = rawBranch.split("#");
|
|
9
|
+
const branchId = parts[1];
|
|
10
|
+
return (_jsx("div", { children: _jsxs(Suspense, { children: [_jsx("h3", { className: 'text-center mt-4', children: "Guest Requirement" }), _jsx(RemoteRoomList, { branchId: branchId, forExtraRequirementCapture: true, classNames: {
|
|
11
|
+
fontTitle: "font-title",
|
|
12
|
+
fontLabel: "font-label",
|
|
13
|
+
formGroup: "form-group",
|
|
14
|
+
buttonPrimary: "btn-primary-global",
|
|
15
|
+
buttonSecondary: "btn-secondary-global"
|
|
16
|
+
} })] }) }));
|
|
17
|
+
};
|
|
18
|
+
export default RoomExtraRequirementCapture;
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import React, { Suspense, useContext } from 'react';
|
|
3
|
+
import AppContext from '../../store/AppContext';
|
|
4
|
+
const RemoteRoomFacilityForm = React.lazy(() => import("bookingUIApp/RoomFacilityForm"));
|
|
5
|
+
const RoomFacilityForm = () => {
|
|
6
|
+
const { user } = useContext(AppContext) ?? { user: undefined };
|
|
7
|
+
const rawBranch = user?.branchId ?? "";
|
|
8
|
+
const parts = rawBranch.split("#");
|
|
9
|
+
const branchId = parts[1];
|
|
10
|
+
const isSuperAdmin = user?.roles?.includes("SUPERADMIN") ?? false;
|
|
11
|
+
return (_jsx("div", { children: _jsx(Suspense, { children: _jsx(RemoteRoomFacilityForm, { branchId: branchId, isSuperAdmin: isSuperAdmin, classNames: {
|
|
12
|
+
fontTitle: "font-title",
|
|
13
|
+
fontLabel: "font-label",
|
|
14
|
+
formGroup: "form-group",
|
|
15
|
+
buttonPrimary: "btn-primary-global",
|
|
16
|
+
buttonSecondary: "btn-secondary-global"
|
|
17
|
+
} }) }) }));
|
|
18
|
+
};
|
|
19
|
+
export default RoomFacilityForm;
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import React, { Suspense, useContext } from 'react';
|
|
3
|
+
import AppContext from '../../store/AppContext';
|
|
4
|
+
const RemoteRoomList = React.lazy(() => import("bookingUIApp/RoomList"));
|
|
5
|
+
const RoomReservationAction = () => {
|
|
6
|
+
const { user } = useContext(AppContext) ?? { user: undefined };
|
|
7
|
+
const rawBranch = user?.branchId ?? "";
|
|
8
|
+
const parts = rawBranch.split("#");
|
|
9
|
+
const branchId = parts[1];
|
|
10
|
+
return (_jsx("div", { children: _jsxs(Suspense, { children: [_jsx("h3", { className: 'text-center mt-4', children: "Reservation Action" }), _jsx(RemoteRoomList, { branchId: branchId, forRoomReservationAction: true, classNames: {
|
|
11
|
+
fontTitle: "font-title",
|
|
12
|
+
fontLabel: "font-label",
|
|
13
|
+
formGroup: "form-group",
|
|
14
|
+
buttonPrimary: "btn-primary-global",
|
|
15
|
+
buttonSecondary: "btn-secondary-global"
|
|
16
|
+
} })] }) }));
|
|
17
|
+
};
|
|
18
|
+
export default RoomReservationAction;
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import React, { useContext } from "react";
|
|
3
|
+
import { EnvConfig } from "../../config/EnvConfig";
|
|
4
|
+
import AppContext from "../../store/AppContext";
|
|
5
|
+
const appName = EnvConfig.applicationName || "Application";
|
|
6
|
+
const ReservationCount = React.lazy(() => import("bookingUIApp/ReservationCount"));
|
|
7
|
+
const Home = () => {
|
|
8
|
+
const { user } = useContext(AppContext) ?? { user: undefined };
|
|
9
|
+
const rawBranch = user?.branchId ?? "";
|
|
10
|
+
const parts = rawBranch.split("#");
|
|
11
|
+
const branchId = parts[1];
|
|
12
|
+
return (_jsxs("div", { className: "d-fle justify-content-center align-items-center h-100 flex-wrap", children: [_jsx("div", { className: "px-3 w-100 col-12", children: _jsx(ReservationCount, { branchId: branchId }) }), _jsx("div", { className: "h-75 d-flex justify-content-center align-items-center", children: _jsxs("div", { className: "text-center", children: [_jsxs("h2", { className: "fw-bold", children: [appName, " Dash Board"] }), _jsx("br", {}), _jsxs("h5", { children: ["\uD83D\uDC4B Welcome To ", appName, "! \uD83D\uDE42"] })] }) })] }));
|
|
13
|
+
};
|
|
14
|
+
export default Home;
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
const LoadingSpinner = () => {
|
|
3
|
+
return (_jsx("div", { className: "d-flex justify-content-center align-items-center h-100", children: _jsxs("div", { className: "text-center", children: [_jsx("div", { className: "spinner-border text-primary p-4", role: "status", children: _jsx("span", { className: "visually-hidden", children: "Loading..." }) }), _jsx("h5", { className: "mt-3", children: "Loading..." })] }) }));
|
|
4
|
+
};
|
|
5
|
+
export default LoadingSpinner;
|
|
@@ -0,0 +1,149 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
|
+
import { useState, useEffect } from "react";
|
|
3
|
+
import { useForm } from "react-hook-form";
|
|
4
|
+
import { zodResolver } from "@hookform/resolvers/zod";
|
|
5
|
+
import { toast } from "react-toastify";
|
|
6
|
+
import "react-toastify/dist/ReactToastify.css";
|
|
7
|
+
import { useNavigate } from "react-router-dom";
|
|
8
|
+
import { FaEye, FaEyeSlash } from "react-icons/fa";
|
|
9
|
+
import logo from "../../../src/assets/images/Hotel-Logo.jpg";
|
|
10
|
+
import { signIn, signUp, confirmSignUp, confirmResetPassword, getCurrentUser, confirmSignIn, resetPassword } from "aws-amplify/auth";
|
|
11
|
+
import { signInSchema, registerSchema, confirmSignUpSchema, resetPasswordSchema, forceResetSchema, forgotPasswordSchema, } from "./loginSchema";
|
|
12
|
+
import { ALL, HIDE_SIGN_UP, HIDE_SIGN_UP_IS_NO } from "../../static/constants";
|
|
13
|
+
import { useGetSettingsByPkAndSk } from "../api/settings-api";
|
|
14
|
+
const LoginForm = ({ login }) => {
|
|
15
|
+
const [authMode, setAuthMode] = useState("signin");
|
|
16
|
+
const navigate = useNavigate();
|
|
17
|
+
const [tempUsername, setTempUsername] = useState("");
|
|
18
|
+
const [showPassword, setShowPassword] = useState(false);
|
|
19
|
+
const { settingsByPkAndSk } = useGetSettingsByPkAndSk(ALL, HIDE_SIGN_UP);
|
|
20
|
+
const getSchema = () => {
|
|
21
|
+
switch (authMode) {
|
|
22
|
+
case "signin":
|
|
23
|
+
return signInSchema;
|
|
24
|
+
case "register":
|
|
25
|
+
return registerSchema;
|
|
26
|
+
case "confirm":
|
|
27
|
+
return confirmSignUpSchema;
|
|
28
|
+
case "forgot":
|
|
29
|
+
return forgotPasswordSchema;
|
|
30
|
+
case "reset":
|
|
31
|
+
return resetPasswordSchema;
|
|
32
|
+
case "forceReset":
|
|
33
|
+
return forceResetSchema;
|
|
34
|
+
default:
|
|
35
|
+
return signInSchema;
|
|
36
|
+
}
|
|
37
|
+
};
|
|
38
|
+
const { register, handleSubmit, formState: { errors }, reset, } = useForm({
|
|
39
|
+
resolver: zodResolver(getSchema()),
|
|
40
|
+
defaultValues: {
|
|
41
|
+
username: "",
|
|
42
|
+
email: "",
|
|
43
|
+
password: "",
|
|
44
|
+
confirmPassword: "",
|
|
45
|
+
confirmationCode: "",
|
|
46
|
+
},
|
|
47
|
+
});
|
|
48
|
+
useEffect(() => {
|
|
49
|
+
reset({}, { keepValues: false });
|
|
50
|
+
}, [authMode, reset]);
|
|
51
|
+
const onSubmit = async (data) => {
|
|
52
|
+
try {
|
|
53
|
+
if (authMode === "signin") {
|
|
54
|
+
const res = await signIn({
|
|
55
|
+
username: data.username,
|
|
56
|
+
password: data.password,
|
|
57
|
+
});
|
|
58
|
+
if (res.nextStep?.signInStep === "CONFIRM_SIGN_IN_WITH_NEW_PASSWORD_REQUIRED") {
|
|
59
|
+
reset({
|
|
60
|
+
password: "",
|
|
61
|
+
confirmPassword: "",
|
|
62
|
+
});
|
|
63
|
+
setAuthMode("forceReset");
|
|
64
|
+
return;
|
|
65
|
+
}
|
|
66
|
+
if (res.isSignedIn) {
|
|
67
|
+
const user = await getCurrentUser();
|
|
68
|
+
localStorage.setItem("lastUser", user.username);
|
|
69
|
+
login(true);
|
|
70
|
+
navigate("/");
|
|
71
|
+
reset();
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
if (authMode === "register") {
|
|
75
|
+
const { nextStep } = await signUp({
|
|
76
|
+
username: data.username,
|
|
77
|
+
password: data.password,
|
|
78
|
+
options: { userAttributes: { email: data.email } },
|
|
79
|
+
});
|
|
80
|
+
if (nextStep?.signUpStep === "CONFIRM_SIGN_UP")
|
|
81
|
+
setAuthMode("confirm");
|
|
82
|
+
reset();
|
|
83
|
+
}
|
|
84
|
+
if (authMode === "confirm") {
|
|
85
|
+
await confirmSignUp({
|
|
86
|
+
username: data.username,
|
|
87
|
+
confirmationCode: data.confirmationCode,
|
|
88
|
+
});
|
|
89
|
+
setAuthMode("signin");
|
|
90
|
+
reset();
|
|
91
|
+
}
|
|
92
|
+
if (authMode === "forgot") {
|
|
93
|
+
try {
|
|
94
|
+
await resetPassword({ username: data.username });
|
|
95
|
+
toast.success("Verification code sent to your email!");
|
|
96
|
+
setTempUsername(data.username); // store username for next step
|
|
97
|
+
setAuthMode("reset");
|
|
98
|
+
reset({}, { keepValues: false });
|
|
99
|
+
}
|
|
100
|
+
catch (err) {
|
|
101
|
+
toast.error(err.message || "Failed to send reset code");
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
if (authMode === "reset") {
|
|
105
|
+
try {
|
|
106
|
+
await confirmResetPassword({
|
|
107
|
+
username: tempUsername,
|
|
108
|
+
confirmationCode: data.confirmationCode,
|
|
109
|
+
newPassword: data.password
|
|
110
|
+
});
|
|
111
|
+
toast.success("Password reset successfully!");
|
|
112
|
+
setAuthMode("signin");
|
|
113
|
+
reset();
|
|
114
|
+
}
|
|
115
|
+
catch (error) {
|
|
116
|
+
if (error.name === "ExpiredCodeException") {
|
|
117
|
+
toast.error("Code expired. Request a new one.");
|
|
118
|
+
setAuthMode("forgot");
|
|
119
|
+
return;
|
|
120
|
+
}
|
|
121
|
+
if (error.name === "CodeMismatchException" || error.name === "InvalidParameterException") {
|
|
122
|
+
toast.error("Invalid verification code. Please request a new one.");
|
|
123
|
+
setAuthMode("forgot");
|
|
124
|
+
setTempUsername("");
|
|
125
|
+
reset();
|
|
126
|
+
return;
|
|
127
|
+
}
|
|
128
|
+
toast.error(error.message || "Failed to reset password");
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
if (authMode === "forceReset") {
|
|
132
|
+
await confirmSignIn({ challengeResponse: data.password });
|
|
133
|
+
login(true);
|
|
134
|
+
navigate("/");
|
|
135
|
+
reset();
|
|
136
|
+
}
|
|
137
|
+
}
|
|
138
|
+
catch (err) {
|
|
139
|
+
toast.error(err.message || "Something went wrong");
|
|
140
|
+
}
|
|
141
|
+
};
|
|
142
|
+
const renderInput = (label, type, name) => {
|
|
143
|
+
const isPassword = type === "password";
|
|
144
|
+
return (_jsxs("div", { className: "mb-3 position-relative", children: [_jsxs("div", { className: "input-group", children: [_jsx("input", { type: isPassword ? (showPassword ? "text" : "password") : type, placeholder: label, ...register(name), className: `form-control ${errors[name] ? "is-invalid" : ""}` }), isPassword && (_jsx("span", { className: "input-group-text bg-white", style: { cursor: "pointer" }, onClick: () => setShowPassword((prev) => !prev), children: showPassword ? _jsx(FaEye, { size: 18 }) : _jsx(FaEyeSlash, { size: 18 }) }))] }), errors[name] && (_jsx("div", { className: "invalid-feedback d-block", children: errors[name]?.message }))] }));
|
|
145
|
+
};
|
|
146
|
+
return (_jsx("div", { className: "d-flex justify-content-center align-items-center vh-100 bg-light", children: _jsx("div", { className: "card shadow-sm p-4 p-md-5 w-100", style: { maxWidth: "420px" }, children: _jsxs("form", { onSubmit: handleSubmit(onSubmit), children: [_jsx("div", { className: "d-flex justify-content-center", children: _jsx("img", { className: "w-75 mx-auto mb-4", src: logo }) }), _jsxs("h4", { className: "text-center mb-4 fw-bold", children: [authMode === "signin" && "Sign in to your account", authMode === "register" && "Create a new account", authMode === "confirm" && "Verify your email", authMode === "forgot" && "Forgot Password?", authMode === "reset" && "Reset Password", authMode === "forceReset" && "Set New Password"] }), authMode === "signin" && (_jsxs(_Fragment, { children: [renderInput("Username", "text", "username"), renderInput("Password", "password", "password"), _jsx("button", { type: "submit", className: "btn btn-primary w-100 mb-2", children: "Sign In" }), _jsxs("div", { className: "d-flex justify-content-between", children: [(settingsByPkAndSk && settingsByPkAndSk?.value === HIDE_SIGN_UP_IS_NO) &&
|
|
147
|
+
_jsx("button", { type: "button", className: "btn btn-link p-0", onClick: () => setAuthMode("register"), children: "Create Account" }), _jsx("button", { type: "button", className: "btn btn-link p-0", onClick: () => setAuthMode("forgot"), children: "Forgot Password?" })] })] })), authMode === "register" && (_jsxs(_Fragment, { children: [renderInput("Username", "text", "username"), renderInput("Email", "email", "email"), renderInput("Password", "password", "password"), renderInput("Confirm Password", "password", "confirmPassword"), _jsx("button", { type: "submit", className: "btn btn-success w-100 mb-2", children: "Register" }), _jsx("button", { type: "button", className: "btn btn-link w-100", onClick: () => setAuthMode("signin"), children: "Back to Sign In" })] })), authMode === "confirm" && (_jsxs(_Fragment, { children: [renderInput("Verification Code", "text", "confirmationCode"), _jsx("button", { type: "submit", className: "btn btn-primary w-100 mb-2", children: "Confirm" }), _jsx("button", { type: "button", className: "btn btn-link w-100", onClick: () => setAuthMode("signin"), children: "Back to Sign In" })] })), authMode === "forgot" && (_jsxs(_Fragment, { children: [renderInput("Username", "text", "username"), _jsx("button", { type: "submit", className: "btn btn-warning w-100 mb-2", children: "Send Reset Code" }), _jsx("button", { type: "button", className: "btn btn-link w-100", onClick: () => setAuthMode("signin"), children: "Back to Sign In" })] })), authMode === "reset" && (_jsxs(_Fragment, { children: [renderInput("Verification Code", "text", "confirmationCode"), renderInput("New Password", "password", "password"), renderInput("Confirm New Password", "password", "confirmPassword"), _jsx("button", { type: "submit", className: "btn btn-success w-100 mb-2", children: "Reset Password" }), _jsx("button", { type: "button", className: "btn btn-link w-100", onClick: () => setAuthMode("signin"), children: "Back to Sign In" })] })), authMode === "forceReset" && (_jsxs(_Fragment, { children: [renderInput("New Password", "password", "password"), renderInput("Confirm New Password", "password", "confirmPassword"), _jsx("button", { type: "submit", className: "btn btn-success w-100 mb-2", children: "Update Password" }), _jsx("button", { type: "button", className: "btn btn-link w-100", onClick: () => setAuthMode("signin"), children: "Back to Sign In" })] }))] }) }) }));
|
|
148
|
+
};
|
|
149
|
+
export default LoginForm;
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
// Schema for Sign In
|
|
3
|
+
export const signInSchema = z.object({
|
|
4
|
+
username: z.string().min(1, "Username is required"),
|
|
5
|
+
password: z.string().min(1, "Password is required"),
|
|
6
|
+
});
|
|
7
|
+
// Schema for Register
|
|
8
|
+
export const registerSchema = z.object({
|
|
9
|
+
username: z.string().min(1, "Username is required"),
|
|
10
|
+
email: z.string().email("Invalid email"),
|
|
11
|
+
password: z.string().min(6, "Password must be at least 6 characters"),
|
|
12
|
+
confirmPassword: z.string().min(1, "Confirm Password is required"),
|
|
13
|
+
}).refine((data) => data.password === data.confirmPassword, {
|
|
14
|
+
message: "Passwords do not match",
|
|
15
|
+
path: ["confirmPassword"],
|
|
16
|
+
});
|
|
17
|
+
// Schema for Forgot/Reset Password
|
|
18
|
+
export const resetPasswordSchema = z.object({
|
|
19
|
+
confirmationCode: z.string().min(6, "Code is required"),
|
|
20
|
+
password: z.string().min(8, "Password must be at least 8 chars"),
|
|
21
|
+
confirmPassword: z.string().min(8, "Confirm your password"),
|
|
22
|
+
}).refine((data) => data.password === data.confirmPassword, {
|
|
23
|
+
message: "Passwords do not match",
|
|
24
|
+
path: ["confirmPassword"],
|
|
25
|
+
});
|
|
26
|
+
export const forgotPasswordSchema = z.object({
|
|
27
|
+
username: z.string().min(1, "Username is required"),
|
|
28
|
+
});
|
|
29
|
+
// Schema for Confirm Sign Up
|
|
30
|
+
export const confirmSignUpSchema = z.object({
|
|
31
|
+
username: z.string().min(1, "Username is required"),
|
|
32
|
+
confirmationCode: z.string().min(1, "Verification code is required"),
|
|
33
|
+
});
|
|
34
|
+
// Schema for Force Reset
|
|
35
|
+
export const forceResetSchema = z.object({
|
|
36
|
+
password: z.string().min(8, "Password must be at least 8 characters"),
|
|
37
|
+
confirmPassword: z.string().min(8, "Confirm Password is required"),
|
|
38
|
+
}).refine((data) => data.password === data.confirmPassword, {
|
|
39
|
+
message: "Passwords do not match",
|
|
40
|
+
path: ["confirmPassword"],
|
|
41
|
+
});
|
|
@@ -0,0 +1,135 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
|
+
import { useEffect, useState } from "react";
|
|
3
|
+
import { useForm } from "react-hook-form";
|
|
4
|
+
import { zodResolver } from "@hookform/resolvers/zod";
|
|
5
|
+
import { Form, Col } from "react-bootstrap";
|
|
6
|
+
import { toast, ToastContainer } from "react-toastify";
|
|
7
|
+
import { useBranchSchema } from "./branchSchema";
|
|
8
|
+
import { useCreateBranchMutation, useUpdateBranchMutation, useListBranches } from "../../../api/mapping-api";
|
|
9
|
+
import { logger } from "../../../util/Logger";
|
|
10
|
+
import "../../../styles/button.css";
|
|
11
|
+
import "../../Mappings/MappingForm/MappingForm.css";
|
|
12
|
+
import { SyzyDate } from "../../../util/SyzyDate";
|
|
13
|
+
import { DATE_FORMAT_ISO_YYYY_MM_DD_HH_MM } from "../../../util/dateUtils";
|
|
14
|
+
import FormModal from "../../common/Modal/Modal";
|
|
15
|
+
import ListTable from "../../common/ListTable/ListTable";
|
|
16
|
+
import { BranchTableColumns } from "./BranchTableColumns";
|
|
17
|
+
import FormLabel from "../../common/Form/FormLabel";
|
|
18
|
+
import FormActionButtons from "../../common/Form/FormActionButtons";
|
|
19
|
+
import ListHeader from "../../common/ListTable/ListHeader";
|
|
20
|
+
const BranchMapping = () => {
|
|
21
|
+
const { branchSchema, initiateBranch } = useBranchSchema();
|
|
22
|
+
const createBranchMutation = useCreateBranchMutation();
|
|
23
|
+
const updateBranchMutation = useUpdateBranchMutation();
|
|
24
|
+
const { data: branches, isLoading } = useListBranches();
|
|
25
|
+
// Modal and form states
|
|
26
|
+
const [showModal, setShowModal] = useState(false);
|
|
27
|
+
const [editingBranch, setEditingBranch] = useState(null);
|
|
28
|
+
const isEditMode = Boolean(editingBranch && editingBranch.pk);
|
|
29
|
+
const loading = isEditMode ? updateBranchMutation.isPending : createBranchMutation.isPending;
|
|
30
|
+
const tableLoading = isLoading || createBranchMutation.isPending || updateBranchMutation.isPending;
|
|
31
|
+
const { register, handleSubmit, reset, formState: { errors }, } = useForm({
|
|
32
|
+
resolver: zodResolver(branchSchema),
|
|
33
|
+
defaultValues: initiateBranch,
|
|
34
|
+
mode: "onChange",
|
|
35
|
+
});
|
|
36
|
+
// Reset form values when editing
|
|
37
|
+
useEffect(() => {
|
|
38
|
+
if (isEditMode && editingBranch) {
|
|
39
|
+
reset({
|
|
40
|
+
...editingBranch,
|
|
41
|
+
branchName: editingBranch.sk,
|
|
42
|
+
status: editingBranch.status ?? "ACTIVE",
|
|
43
|
+
createdDt: editingBranch.createdDt ?? new SyzyDate().toDateFormatString(DATE_FORMAT_ISO_YYYY_MM_DD_HH_MM),
|
|
44
|
+
});
|
|
45
|
+
}
|
|
46
|
+
else {
|
|
47
|
+
reset(initiateBranch);
|
|
48
|
+
}
|
|
49
|
+
}, [editingBranch, isEditMode, reset]);
|
|
50
|
+
// Open modal for editing
|
|
51
|
+
const handleEdit = (branch) => {
|
|
52
|
+
setEditingBranch(branch);
|
|
53
|
+
setShowModal(true);
|
|
54
|
+
reset({
|
|
55
|
+
...branch,
|
|
56
|
+
branchName: branch.sk,
|
|
57
|
+
status: branch.status ?? "ACTIVE",
|
|
58
|
+
createdDt: branch.createdDt ?? new SyzyDate().toDateFormatString(DATE_FORMAT_ISO_YYYY_MM_DD_HH_MM),
|
|
59
|
+
});
|
|
60
|
+
};
|
|
61
|
+
// Form submit handler
|
|
62
|
+
const onSubmit = async (data) => {
|
|
63
|
+
try {
|
|
64
|
+
// EDIT MODE
|
|
65
|
+
if (isEditMode && editingBranch?.pk) {
|
|
66
|
+
const skChanged = data.branchName !== editingBranch.sk;
|
|
67
|
+
if (skChanged) {
|
|
68
|
+
// Step 1: mark old row as INACTIVE
|
|
69
|
+
await updateBranchMutation.mutateAsync({
|
|
70
|
+
pk: editingBranch.pk,
|
|
71
|
+
sk: editingBranch.sk,
|
|
72
|
+
branchAddress: editingBranch.branchAddress,
|
|
73
|
+
branchContactNumber: editingBranch.branchContactNumber,
|
|
74
|
+
status: "INACTIVE",
|
|
75
|
+
createdDt: editingBranch.createdDt,
|
|
76
|
+
});
|
|
77
|
+
// Step 2: create new row with new SK
|
|
78
|
+
await updateBranchMutation.mutateAsync({
|
|
79
|
+
pk: editingBranch.pk,
|
|
80
|
+
sk: data.branchName,
|
|
81
|
+
branchAddress: data.branchAddress,
|
|
82
|
+
branchContactNumber: data.branchContactNumber,
|
|
83
|
+
status: "ACTIVE",
|
|
84
|
+
createdDt: new SyzyDate().toDateFormatString(DATE_FORMAT_ISO_YYYY_MM_DD_HH_MM),
|
|
85
|
+
});
|
|
86
|
+
toast.success("Branch renamed and updated successfully!");
|
|
87
|
+
setShowModal(false);
|
|
88
|
+
setEditingBranch(null);
|
|
89
|
+
return;
|
|
90
|
+
}
|
|
91
|
+
// NORMAL update (no rename)
|
|
92
|
+
await updateBranchMutation.mutateAsync({
|
|
93
|
+
pk: editingBranch.pk,
|
|
94
|
+
sk: data.branchName,
|
|
95
|
+
branchAddress: data.branchAddress,
|
|
96
|
+
branchContactNumber: data.branchContactNumber,
|
|
97
|
+
status: data.status ?? "ACTIVE",
|
|
98
|
+
createdDt: editingBranch.createdDt ?? new Date().toISOString(),
|
|
99
|
+
});
|
|
100
|
+
toast.success("Branch updated successfully!");
|
|
101
|
+
setShowModal(false);
|
|
102
|
+
setEditingBranch(null);
|
|
103
|
+
return;
|
|
104
|
+
}
|
|
105
|
+
// CREATE MODE
|
|
106
|
+
await createBranchMutation.mutateAsync({
|
|
107
|
+
branchName: data.branchName,
|
|
108
|
+
branchAddress: data.branchAddress,
|
|
109
|
+
branchContactNumber: data.branchContactNumber,
|
|
110
|
+
status: data.status ?? "ACTIVE",
|
|
111
|
+
});
|
|
112
|
+
toast.success("Branch created successfully!");
|
|
113
|
+
setShowModal(false);
|
|
114
|
+
reset(initiateBranch);
|
|
115
|
+
}
|
|
116
|
+
catch (err) {
|
|
117
|
+
logger.error("Branch operation error", err);
|
|
118
|
+
toast.error("Branch operation failed");
|
|
119
|
+
}
|
|
120
|
+
};
|
|
121
|
+
return (_jsxs(_Fragment, { children: [_jsx(ToastContainer, {}), _jsxs("div", { className: "container", children: [_jsx(ListHeader, { title: "Branches List", buttonLabel: "Add Branch", onButtonClick: () => {
|
|
122
|
+
reset(initiateBranch);
|
|
123
|
+
setEditingBranch(null);
|
|
124
|
+
setShowModal(true);
|
|
125
|
+
} }), isLoading ? null : (_jsx(ListTable, { columns: BranchTableColumns, data: branches ?? [], emptyMessage: "No branches found", onEdit: handleEdit, loading: tableLoading }))] }), _jsx(FormModal, { show: showModal, title: isEditMode ? "Edit Branch" : "Create Branch", onClose: () => {
|
|
126
|
+
setShowModal(false);
|
|
127
|
+
setEditingBranch(null);
|
|
128
|
+
reset(initiateBranch);
|
|
129
|
+
}, children: _jsxs(Form, { className: "branch-form", onSubmit: handleSubmit(onSubmit), children: [_jsxs(Col, { children: [_jsx(FormLabel, { label: "Branch Name", required: true }), _jsx(Form.Control, { ...register("branchName"), isInvalid: !!errors.branchName, placeholder: "Enter branch name" }), _jsx(Form.Text, { className: "text-danger", children: errors.branchName?.message })] }), _jsxs(Col, { children: [_jsx(FormLabel, { label: "Branch Address", required: true }), _jsx(Form.Control, { ...register("branchAddress"), isInvalid: !!errors.branchAddress, placeholder: "Enter branch address" }), _jsx(Form.Text, { className: "text-danger", children: errors.branchAddress?.message })] }), _jsxs(Col, { children: [_jsx(FormLabel, { label: "Contact Number", required: true }), _jsx(Form.Control, { ...register("branchContactNumber"), isInvalid: !!errors.branchContactNumber, placeholder: "Enter branch contact number" }), _jsx(Form.Text, { className: "text-danger", children: errors.branchContactNumber?.message })] }), _jsxs(Col, { children: [_jsx(FormLabel, { label: "Status" }), _jsxs(Form.Select, { ...register("status"), children: [_jsx("option", { value: "ACTIVE", children: "ACTIVE" }), _jsx("option", { value: "INACTIVE", children: "INACTIVE" })] })] }), _jsx(FormActionButtons, { isEditMode: isEditMode, loading: loading, onClear: () => {
|
|
130
|
+
setShowModal(false);
|
|
131
|
+
setEditingBranch(null);
|
|
132
|
+
reset(initiateBranch);
|
|
133
|
+
} })] }) })] }));
|
|
134
|
+
};
|
|
135
|
+
export default BranchMapping;
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import { Status } from "../../../domain/type/StatusEnum";
|
|
3
|
+
export const BranchTableColumns = [
|
|
4
|
+
{
|
|
5
|
+
header: "Branch Name",
|
|
6
|
+
accessor: (row) => row.sk,
|
|
7
|
+
},
|
|
8
|
+
{
|
|
9
|
+
header: "Address",
|
|
10
|
+
accessor: "branchAddress",
|
|
11
|
+
},
|
|
12
|
+
{
|
|
13
|
+
header: "Contact Number",
|
|
14
|
+
accessor: "branchContactNumber",
|
|
15
|
+
},
|
|
16
|
+
{
|
|
17
|
+
header: "Status",
|
|
18
|
+
accessor: (row) => (_jsx("span", { className: `status-message ${row.status === Status.Active ? "text-success" : "text-danger"}`, children: row.status })),
|
|
19
|
+
align: "center",
|
|
20
|
+
},
|
|
21
|
+
];
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
|
+
import { useEffect, useState } from "react";
|
|
3
|
+
import MappingForm from "../MappingForm/MappingForm";
|
|
4
|
+
import FormModal from "../../common/Modal/Modal";
|
|
5
|
+
import ListTable from "../../common/ListTable/ListTable";
|
|
6
|
+
import { toast, ToastContainer } from "react-toastify";
|
|
7
|
+
import { Status } from "../../../domain/type/StatusEnum";
|
|
8
|
+
import { useListBranches, useListProfiles, useCreateMappingMutation, useUpdateMappingMutation, getRoleMappingByUserIdAndRoleNameFun, fetchBranchUserMappings } from "../../../api/mapping-api";
|
|
9
|
+
import { EntityTypes } from "../../../domain/type/EntityTypes";
|
|
10
|
+
import { SyzyDate } from "../../../util/SyzyDate";
|
|
11
|
+
import { DATE_FORMAT_ISO_YYYY_MM_DD_HH_MM_SS } from "../../../util/dateUtils";
|
|
12
|
+
import { logger } from "../../../util/Logger";
|
|
13
|
+
import { BranchUserTableColumns } from "./MappingTableColumns";
|
|
14
|
+
import ListHeader from "../../common/ListTable/ListHeader";
|
|
15
|
+
const MappingFormBranchUser = () => {
|
|
16
|
+
const [showModal, setShowModal] = useState(false);
|
|
17
|
+
const [editingRow, setEditingRow] = useState();
|
|
18
|
+
const [branches, setBranches] = useState([]);
|
|
19
|
+
const [users, setUsers] = useState([]);
|
|
20
|
+
const [mappings, setMappings] = useState([]);
|
|
21
|
+
const [loading, setLoading] = useState(true);
|
|
22
|
+
const currentISODate = new SyzyDate().toDateFormatString(DATE_FORMAT_ISO_YYYY_MM_DD_HH_MM_SS);
|
|
23
|
+
const { data: branchList, isLoading } = useListBranches();
|
|
24
|
+
const { data: profiles, isLoading: isProfilesLoading } = useListProfiles();
|
|
25
|
+
const createMappingMutation = useCreateMappingMutation();
|
|
26
|
+
const updateMappingMutation = useUpdateMappingMutation();
|
|
27
|
+
const tableLoading = isLoading || isProfilesLoading || createMappingMutation.isPending || updateMappingMutation.isPending;
|
|
28
|
+
/** Load branches */
|
|
29
|
+
useEffect(() => {
|
|
30
|
+
if (branchList) {
|
|
31
|
+
setBranches(branchList.map((b) => ({ id: b.pk, name: b.sk })));
|
|
32
|
+
}
|
|
33
|
+
}, [branchList]);
|
|
34
|
+
/** Load users */
|
|
35
|
+
useEffect(() => {
|
|
36
|
+
if (profiles) {
|
|
37
|
+
setUsers(profiles.map((p) => ({ id: p.sk, name: p.name })));
|
|
38
|
+
}
|
|
39
|
+
}, [profiles]);
|
|
40
|
+
/* ---------------- Load Mappings ---------------- */
|
|
41
|
+
const loadMappings = async () => {
|
|
42
|
+
try {
|
|
43
|
+
if (!branchList)
|
|
44
|
+
return;
|
|
45
|
+
const branchMap = {};
|
|
46
|
+
branchList.forEach((b) => {
|
|
47
|
+
branchMap[b.pk.replace("BRANCH#", "")] = b.sk;
|
|
48
|
+
});
|
|
49
|
+
const result = await fetchBranchUserMappings(branchMap);
|
|
50
|
+
const enriched = result.map((m) => {
|
|
51
|
+
const branchId = m.pk.replace("BRANCH#", "");
|
|
52
|
+
return {
|
|
53
|
+
...m,
|
|
54
|
+
branchId,
|
|
55
|
+
branchName: branchMap[branchId] ?? "Unknown Branch",
|
|
56
|
+
};
|
|
57
|
+
});
|
|
58
|
+
setMappings(enriched);
|
|
59
|
+
}
|
|
60
|
+
catch (err) {
|
|
61
|
+
toast.error("Failed to load mappings");
|
|
62
|
+
}
|
|
63
|
+
finally {
|
|
64
|
+
setLoading(false);
|
|
65
|
+
}
|
|
66
|
+
};
|
|
67
|
+
useEffect(() => {
|
|
68
|
+
loadMappings();
|
|
69
|
+
}, [branchList]);
|
|
70
|
+
/* ---------------- Edit / Add ---------------- */
|
|
71
|
+
const handleEdit = (row) => {
|
|
72
|
+
setEditingRow(row);
|
|
73
|
+
setShowModal(true);
|
|
74
|
+
};
|
|
75
|
+
const handleAdd = () => {
|
|
76
|
+
setEditingRow(undefined);
|
|
77
|
+
setShowModal(true);
|
|
78
|
+
};
|
|
79
|
+
/* ---------------- Submit ---------------- */
|
|
80
|
+
const handleSubmit = async (data) => {
|
|
81
|
+
try {
|
|
82
|
+
for (const map of data) {
|
|
83
|
+
const user = users.find(u => u.id === map.sourceId);
|
|
84
|
+
const branch = branches.find(b => b.id === map.branchId);
|
|
85
|
+
if (!user || !branch)
|
|
86
|
+
continue;
|
|
87
|
+
const payload = {
|
|
88
|
+
pk: `BRANCH#${map.branchId}`,
|
|
89
|
+
sk: `USER#${user.id}`,
|
|
90
|
+
branchName: branch.name,
|
|
91
|
+
entity: EntityTypes.USER,
|
|
92
|
+
userId: user.id,
|
|
93
|
+
userName: user.name,
|
|
94
|
+
roleId: "null",
|
|
95
|
+
roleName: "null",
|
|
96
|
+
componentId: "null",
|
|
97
|
+
componentTitle: "null",
|
|
98
|
+
status: map.status,
|
|
99
|
+
createdDt: editingRow?.createdDt || currentISODate,
|
|
100
|
+
createdBy: `${user.id}#${user.name}`,
|
|
101
|
+
disabledDt: map.status === Status.Inactive ? currentISODate : "",
|
|
102
|
+
};
|
|
103
|
+
const isBranchChanged = editingRow && editingRow.branchId !== map.branchId;
|
|
104
|
+
const isUserChanged = editingRow && editingRow.userId !== user.id;
|
|
105
|
+
if (editingRow && (isBranchChanged || isUserChanged)) {
|
|
106
|
+
await updateMappingMutation.mutateAsync({
|
|
107
|
+
pk: editingRow.pk,
|
|
108
|
+
sk: `USER#${editingRow.userId}`,
|
|
109
|
+
branchName: editingRow.branchName,
|
|
110
|
+
entity: EntityTypes.USER,
|
|
111
|
+
userId: editingRow.userId,
|
|
112
|
+
userName: editingRow.userName,
|
|
113
|
+
roleId: "null",
|
|
114
|
+
roleName: "null",
|
|
115
|
+
componentId: "null",
|
|
116
|
+
componentTitle: "null",
|
|
117
|
+
status: Status.Inactive,
|
|
118
|
+
createdDt: editingRow.createdDt,
|
|
119
|
+
createdBy: `${user.id}#${user.name}`,
|
|
120
|
+
disabledDt: currentISODate,
|
|
121
|
+
});
|
|
122
|
+
}
|
|
123
|
+
const existing = await getRoleMappingByUserIdAndRoleNameFun(payload.pk, payload.sk);
|
|
124
|
+
if (existing) {
|
|
125
|
+
await updateMappingMutation.mutateAsync(payload);
|
|
126
|
+
}
|
|
127
|
+
else {
|
|
128
|
+
await createMappingMutation.mutateAsync(payload);
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
toast.success("Branch-User mapping saved successfully");
|
|
132
|
+
setShowModal(false);
|
|
133
|
+
loadMappings();
|
|
134
|
+
}
|
|
135
|
+
catch (err) {
|
|
136
|
+
logger.error(err);
|
|
137
|
+
toast.error("Mapping failed");
|
|
138
|
+
}
|
|
139
|
+
};
|
|
140
|
+
/* ---------------- Render ---------------- */
|
|
141
|
+
return (_jsxs(_Fragment, { children: [_jsx(ToastContainer, {}), _jsxs("div", { className: "container", children: [_jsx(ListHeader, { title: "Branch & User Mappings List", buttonLabel: "Add Mapping", onButtonClick: handleAdd }), loading ? null : (_jsx(ListTable, { columns: BranchUserTableColumns, data: mappings, emptyMessage: "No branch-user mappings found", onEdit: handleEdit, loading: tableLoading })), _jsx(FormModal, { show: showModal, title: editingRow ? "Edit Branch-User Mapping" : "Assign Branch to User", onClose: () => setShowModal(false), size: "lg", children: _jsx(MappingForm, { mode: "branch-user", hideBranch: false, hideTarget: true, branchOptions: branches, sourceLabel: "User", targetLabel: "", sourceOptions: users, targetOptions: [], onSubmit: handleSubmit, initialMapping: editingRow
|
|
142
|
+
? {
|
|
143
|
+
branchId: editingRow.branchId,
|
|
144
|
+
sourceId: editingRow.userId,
|
|
145
|
+
sourceName: editingRow.userName,
|
|
146
|
+
status: editingRow.status,
|
|
147
|
+
}
|
|
148
|
+
: undefined }) })] })] }));
|
|
149
|
+
};
|
|
150
|
+
export default MappingFormBranchUser;
|