diff --git a/src/layout/MainLayout/Header/index.js b/src/layout/MainLayout/Header/index.js
index a85a0c2..2f570ba 100644
--- a/src/layout/MainLayout/Header/index.js
+++ b/src/layout/MainLayout/Header/index.js
@@ -149,6 +149,15 @@ function Header(props) {
<>>
}
+ {
+ isGranted("MAINTAIN_DEMANDNOTE") ?
+
+ Export for GDN
+
+ :
+ <>>
+ }
+
:
diff --git a/src/pages/DemandNote/Export/DataGrid.js b/src/pages/DemandNote/Export/DataGrid.js
new file mode 100644
index 0000000..c0cc4de
--- /dev/null
+++ b/src/pages/DemandNote/Export/DataGrid.js
@@ -0,0 +1,204 @@
+// material-ui
+import * as React from 'react';
+import * as UrlUtils from "utils/ApiPathConst";
+import * as DateUtils from "utils/DateUtils";
+import * as FormatUtils from "utils/FormatUtils";
+// import * as PublicNoteStatusUtils from "utils/statusUtils/PublicNoteStatusUtils"
+import { FiDataGrid } from "components/FiDataGrid";
+import { clickableLink } from 'utils/CommonFunction';
+// ==============================|| EVENT TABLE ||============================== //
+
+export default function SearchPublicNoticeTable({ searchCriteria,}) {
+ const _sx = {
+ padding: "4 2 4 2",
+ boxShadow: 1,
+ border: 1,
+ borderColor: '#DDD',
+ '& .MuiDataGrid-cell': {
+ borderTop: 1,
+ borderBottom: 1,
+ borderColor: "#EEE"
+ },
+ '& .MuiDataGrid-footerContainer': {
+ border: 1,
+ borderColor: "#EEE"
+ }
+ }
+ const [_searchCriteria, set_searchCriteria] = React.useState(searchCriteria);
+ React.useEffect(() => {
+ set_searchCriteria(searchCriteria);
+ }, [searchCriteria]);
+
+ const handleEditClick = (params) => () => {
+ window.open('/application/' + params.row.id);
+ };
+
+ const columns = [
+ {
+ id: 'itemNo',
+ field: 'itemNo',
+ headerName: 'Item No.',
+ flex: 1,
+ minWidth: 50,
+ renderCell: (params) => {
+ // const regex = /^(\D+)(\d+)$/;
+ // const [, category, itemNo] = params.row.groupNo.match(regex);
+ const itemNo = parseInt(params.row.groupNo.substring(1))
+ return itemNo
+ },
+ },
+ {
+ field: 'category',
+ headerName: 'Category',
+ flex: 1,
+ minWidth: 50,
+ renderCell: (params) => {
+ const category = params.row.groupNo.substring(0, 1);
+ return category
+ }
+ },
+ {
+ id: 'appNo',
+ field: 'appNo',
+ headerName: 'App No.',
+ flex: 1,
+ minWidth: 50,
+ renderCell: (params) => {
+ return clickableLink('/application/' + params.row.id, params.row.appNo)
+ },
+ },
+ {
+ id: 'user',
+ field: 'user',
+ headerName: 'User',
+ flex: 1,
+ minWidth: 50,
+ renderCell: (params) => {
+ // let user = params.row.enCompanyName != null ? params.row.enCompanyName : params.row.chCompanyName;
+ let user = params.row.contactPerson;
+ // user = user != null ? user : "";
+ if (params.row.sysType != null && params.row.sysType == "dummy"){
+ user = "Dummy - PD"
+ }
+ return
+ {user}
+
;
+ }
+ },
+ {
+ id: 'contactPerson',
+ field: 'contactPerson',
+ headerName: 'Customer Name',
+ flex: 1,
+ minWidth: 50,
+ renderCell: (params) => {
+ let company = params.row.enCompanyName != null ? params.row.enCompanyName : params.row.chCompanyName;
+ company = company != null ? company : "";
+ if (params.row.sysType != null && params.row.sysType == "dummy"){
+ company = params.row.contactPerson
+ }
+ return
+ {company}
+
;
+ }
+ },
+ {
+ id: 'careOf',
+ field: 'careOf',
+ headerName: "Customer's Client/Case Node.",
+ flex: 2,
+ minWidth: 200,
+ renderCell: (params) => {
+ return <>{(params?.value)}>;
+ }
+ },
+ {
+ id: 'dimension',
+ field: 'dimension',
+ headerName: 'Dimension',
+ flex: 1,
+ minWidth: 100,
+ valueGetter: (params) => {
+ let length = params.row.length
+ let colCount = params.row.colCount
+ let noOfPages = params.row.noOfPages
+ let dimension = 0
+ if (noOfPages != null){
+ dimension = length*colCount*noOfPages
+ }else{
+ dimension = length*colCount
+ }
+ return dimension;
+ }
+ },
+ {
+ id: 'fee',
+ field: 'fee',
+ headerName: 'Amount(HK$)',
+ flex: 1,
+ minWidth: 100,
+ valueGetter: (params) => {
+ return FormatUtils.currencyFormat(params?.value);
+ }
+ },
+ {
+ id: 'emailAddress',
+ field: 'emailAddress',
+ headerName: 'Contact E-mail Address',
+ flex:2,
+ minWidth: 100,
+ valueGetter: (params) => {
+ let email = params.row.emailBus != null && params.row.emailBus != "" ? params.row.emailBus : params.row.emailAddress;
+ email = email != null ? email : "";
+ if (params.row.sysType != null && params.row.sysType == "dummy"){
+ email = params.row.remarks
+ }
+ return email;
+ },
+ },
+ {
+ id: 'deadline',
+ field: 'deadline',
+ headerName: 'Payment Deadline',
+ flex: 2,
+ minWidth: 100,
+ renderCell: (params) => {
+ return <>{DateUtils.dateStr(params.row.closingDate) + " 12noon"}>;
+ }
+ },
+ {
+ id: 'exported',
+ field: 'exported',
+ headerName: 'Exported',
+ flex: 1,
+ minWidth: 50,
+ renderCell: (params) => {
+ let exported = params.row.exported ? "Y" : "N";
+ return exported
+ }
+ },
+ ];
+
+ return (
+
+
+ 'auto'}
+ columns={columns}
+ customPageSize={10}
+ onRowDoubleClick={handleEditClick}
+ doLoad={{
+ url: _searchCriteria.issueId>0?UrlUtils.GDN_VIEW:null,
+ params: {
+ issueId: _searchCriteria.issueId
+ },
+ // callback: (responseData) => {
+ // setPaymentCount(responseData.paymentCount);
+ // setPublishCount(responseData.publishCount);
+ // }
+ }}
+ />
+
+ );
+}
diff --git a/src/pages/DemandNote/Export/SearchForm.js b/src/pages/DemandNote/Export/SearchForm.js
new file mode 100644
index 0000000..849867a
--- /dev/null
+++ b/src/pages/DemandNote/Export/SearchForm.js
@@ -0,0 +1,278 @@
+// material-ui
+import {
+ Button,
+ Grid, TextField,
+ Autocomplete,
+ Typography,
+ Dialog, DialogTitle, DialogContent, DialogActions,
+} from '@mui/material';
+import MainCard from "components/MainCard";
+import * as React from "react";
+import * as FormatUtils from "utils/FormatUtils";
+import * as DateUtils from "utils/DateUtils";
+import * as UrlUtils from "utils/ApiPathConst";
+import * as HttpUtils from "utils/HttpUtils";
+// import { useNavigate } from "react-router-dom";
+// import { notifyDownloadSuccess } from 'utils/CommonFunction';
+import { PNSPS_BUTTON_THEME } from "../../../themes/buttonConst";
+import { ThemeProvider } from "@emotion/react";
+import { useIntl } from "react-intl";
+
+
+// ==============================|| DASHBOARD - DEFAULT ||============================== //
+
+
+const SearchPublicNoticeForm = ({ applySearch, issueComboData }) => {
+
+ const [isFailPopUp, setIsFailPopUp] = React.useState(false);
+ const [failText, setFailText] = React.useState("");
+
+ const [confirmPopUp, setConfirmPopUp] = React.useState(false);
+ const [dueDate, setDueDate] = React.useState(DateUtils.dateValue(DateUtils.dateValue((new Date().setDate(new Date().getDate() + 1)))));
+
+ // const [isSuccessPopUp, setIsSuccessPopUp] = React.useState(false);
+ // const [resultCount, setResultCount] = React.useState(0);
+ // const [dnIdList, setDnIdList] = React.useState([]);
+
+ const [issueSelected, setIssueSelected] = React.useState({});
+ // const [paymentCount, setPaymentCount] = React.useState(0);
+ // const [publishCount, setPublishCount] = React.useState(0);
+ const [issueCombo, setIssueCombo] = React.useState([]);
+ const [waitDownload, setWaitDownload] = React.useState(false);
+ // const navigate = useNavigate()
+
+ const intl = useIntl();
+ const { locale } = intl;
+
+ React.useEffect(() => {
+ if (issueComboData && issueComboData.length > 0) {
+ setIssueCombo(issueComboData);
+ }
+ }, [issueComboData]);
+
+ // React.useEffect(() => {
+ // setPaymentCount(_paymentCount);
+ // }, [_paymentCount]);
+
+ // React.useEffect(() => {
+ // setPublishCount(_publishCount);
+ // }, [_publishCount]);
+
+ React.useEffect(() => {
+ onPreView();
+ }, [issueSelected]);
+
+ function getIssueLabel(data) {
+ let issueYear = data.issueYear
+ let volume = data.volume;
+ let issueNo = data.issueNo;
+ let issueDate = data.issueDate;
+ if (locale === 'zh-HK') {
+ return issueYear
+ + " 第" + volume + "卷,"
+ + " 第" + issueNo + "期,"
+ + " " + DateUtils.dateFormat(issueDate, "YYYY年MM月DD日")
+ + " (" + DateUtils.getWeekdayStr_ZH(issueDate) + ")";
+ } else if (locale === 'zh-CN') {
+ return issueYear
+ + " 第" + volume + "卷,"
+ + " 第" + issueNo + "期,"
+ + " " + DateUtils.dateFormat(issueDate, "YYYY年MM月DD日")
+ + " (" + DateUtils.getWeekdayStr_CN(issueDate) + ")";
+ }
+ return issueYear
+ + " Vol. " + FormatUtils.zeroPad(volume, 3)
+ + ", No. " + FormatUtils.zeroPad(issueNo, 2)
+ + ", " + DateUtils.dateFormat(issueDate, "D MMM YYYY (ddd)");
+ }
+
+ const onSubmit = () => {
+ if (!issueSelected?.id) {
+ setFailText("Fail Create: Please select Gazette Issue.");
+ setIsFailPopUp(true);
+ return;
+ } else {
+ setDueDate(DateUtils.dateValue((new Date().setDate(new Date().getDate() + 1))));
+ doDnExport();
+ }
+ };
+
+ const doDnExport= () => {
+ // setConfirmPopUp(false);
+ setWaitDownload(true)
+ HttpUtils.fileDownload({
+ url: UrlUtils.GDN_EXPORT,
+ params: {
+ issueId: issueSelected.id
+ },
+ onResponse: () => {
+ setTimeout(()=> setWaitDownload(false), 500)
+ }
+ });
+ }
+
+ // const fileDownload = () => {
+ // HttpUtils.fileDownload({
+ // method: 'post',
+ // url: UrlUtils.DEMAND_NOTE_EXPORT,
+ // params: {
+ // "dnIdList": dnIdList
+ // },
+ // onSuccess: function () {
+ // notifyDownloadSuccess();
+ // }
+ // });
+ // }
+
+ // const onNavigate = () => {
+ // setIsSuccessPopUp(false);
+ // if (resultCount > 0)
+ // navigate('/paymentPage/demandNote');
+ // };
+
+ const onPreView = () => {
+ if (!issueSelected?.id) {
+ return;
+ }
+ const temp = {
+ issueId: issueSelected.id,
+ };
+ applySearch(temp);
+ };
+
+ return (
+
+
+
+
+
+
+
+
+
+
+ );
+};
+
+export default SearchPublicNoticeForm;
diff --git a/src/pages/DemandNote/Export/index.js b/src/pages/DemandNote/Export/index.js
new file mode 100644
index 0000000..16d3e61
--- /dev/null
+++ b/src/pages/DemandNote/Export/index.js
@@ -0,0 +1,103 @@
+// material-ui
+import {
+ Grid,
+ Typography,
+ Stack
+} from '@mui/material';
+import MainCard from "components/MainCard";
+import * as UrlUtils from "utils/ApiPathConst";
+import * as HttpUtils from "utils/HttpUtils";
+import * as React from "react";
+
+
+import Loadable from 'components/Loadable';
+const LoadingComponent = Loadable(React.lazy(() => import('pages/extra-pages/LoadingComponent')));
+const SearchForm = Loadable(React.lazy(() => import('./SearchForm')));
+const EventTable = Loadable(React.lazy(() => import('./DataGrid')));
+import titleBackgroundImg from 'assets/images/dashboard/gazette-bar.png'
+
+const BackgroundHead = {
+ backgroundImage: `url(${titleBackgroundImg})`,
+ width: '100%',
+ height: '100%',
+ backgroundSize: 'contain',
+ backgroundRepeat: 'no-repeat',
+ backgroundColor: '#0C489E',
+ backgroundPosition: 'right'
+}
+
+// ==============================|| DASHBOARD - DEFAULT ||============================== //
+
+const Index = () => {
+
+ const [issueCombo, setIssueCombo] = React.useState([]);
+ const [searchCriteria, setSearchCriteria] = React.useState({});
+ const [onReady, setOnReady] = React.useState(false);
+
+ // const [paymentCount, setPaymentCount] = React.useState(0);
+ // const [publishCount, setPublishCount] = React.useState(0);
+
+ React.useEffect(() => {
+ getIssueCombo();
+ }, []);
+
+ React.useEffect(() => {
+ setOnReady(true);
+ }, [searchCriteria]);
+
+ function getIssueCombo() {
+ HttpUtils.get({
+ url: UrlUtils.GET_ISSUE_COMBO,
+ onSuccess: function (responseData) {
+ let combo = responseData;
+ setIssueCombo(combo);
+ }
+ });
+ }
+
+
+ function applySearch(input) {
+ setSearchCriteria(input);
+ }
+
+ return (
+ !onReady ?
+
+ :
+
+
+
+
+
+ Export for GDN (Non Creditor)
+
+
+
+
+ {/*row 1*/}
+
+
+
+ {/*row 2*/}
+
+
+
+
+
+
+ );
+};
+
+export default Index;
diff --git a/src/pages/Holiday/DataGrid.js b/src/pages/Holiday/DataGrid.js
index 5120dff..bca77f6 100644
--- a/src/pages/Holiday/DataGrid.js
+++ b/src/pages/Holiday/DataGrid.js
@@ -15,8 +15,8 @@ export default function HolidayTable({ recordList }) {
// const navigate = useNavigate()
useEffect(() => {
- // console.log(recordList)
- setRows(recordList);
+ console.log(recordList)
+ setRows(recordList.records);
}, [recordList]);
const columns = [
diff --git a/src/pages/Holiday/index.js b/src/pages/Holiday/index.js
index 6401ffe..9a7d59d 100644
--- a/src/pages/Holiday/index.js
+++ b/src/pages/Holiday/index.js
@@ -73,7 +73,7 @@ const Index = () => {
url: UrlUtils.GET_HOLIDAY,
params: searchCriteria,
onSuccess: (responseData) => {
- // console.log(comboData)
+ // console.log(responseData)
setRecord(responseData);
if (comboData.length == 0) {
loadCombo();
diff --git a/src/pages/PublicNotice/ListPanel/PendingPaymentTab.js b/src/pages/PublicNotice/ListPanel/PendingPaymentTab.js
index 24aaaa0..3d7fce2 100644
--- a/src/pages/PublicNotice/ListPanel/PendingPaymentTab.js
+++ b/src/pages/PublicNotice/ListPanel/PendingPaymentTab.js
@@ -24,6 +24,7 @@ import { useNavigate } from "react-router-dom";
import {
isORGLoggedIn,
} from "utils/Utils";
+import { dateStr } from "utils/DateUtils";
import { ThemeProvider, useTheme } from "@emotion/react";
import { PNSPS_BUTTON_THEME } from "../../../themes/buttonConst";
import { FormattedMessage, useIntl } from "react-intl";
@@ -210,25 +211,30 @@ export default function SubmittedTab({ setCount, url }) {
},
},
{
- id: 'paymentMethod',
- field: 'paymentMethod',
- headerName: intl.formatMessage({ id: 'paymentMethod' }),
+ id: 'paymentMethodAndDeadLine',
+ field: 'paymentMethodAndDeadLine',
+ headerName: intl.formatMessage({ id: 'paymentMethodAndDeadLine' }),
width: isMdOrLg ? 'auto' : 160,
flex: isMdOrLg ? 1 : undefined,
- renderCell: (params) => {
- return params.row.paymentMethod!=null?intl.formatMessage({ id: utils.getPaymentMethod(params.row.paymentMethod)}):""
- },
- },
- {
- id: 'paymentMethod',
- field: 'paymentMethod',
- headerName: intl.formatMessage({ id: 'paymentMethod' }),
- width: isMdOrLg ? 'auto' : 160,
- flex: isMdOrLg ? 1 : undefined,
- renderCell: (params) => {
- return params.row.paymentMethod!=null?intl.formatMessage({ id: utils.getPaymentMethod(params.row.paymentMethod)}):""
- },
+ renderCell: (params) => (
+
+
+
{dateStr(params.row.closingDateOff)}
+
+ )
},
+ // {
+ // id: 'closingDateOff',
+ // field: 'closingDateOff',
+ // headerName: intl.formatMessage({ id: 'paymentMethod' }),
+ // width: isMdOrLg ? 'auto' : 160,
+ // flex: isMdOrLg ? 1 : undefined,
+ // renderCell: (params) => {
+ // // console.log(params)
+ // let closingDateOff = params.row.closingDateOff;
+ // return {dateStr(closingDateOff)}
+ // },
+ // },
{
id: 'status',
field: 'status',
diff --git a/src/pages/PublicNotice/Search_GLD/DataGrid.js b/src/pages/PublicNotice/Search_GLD/DataGrid.js
index 8de6f3a..6e6ed13 100644
--- a/src/pages/PublicNotice/Search_GLD/DataGrid.js
+++ b/src/pages/PublicNotice/Search_GLD/DataGrid.js
@@ -17,6 +17,7 @@ import { useNavigate } from "react-router-dom";
import { FiDataGrid } from "components/FiDataGrid";
import { notifyActionSuccess, clickableLink } from 'utils/CommonFunction';
import { FormattedMessage, useIntl } from "react-intl";
+import * as utils from "auth/utils"
// ==============================|| EVENT TABLE ||============================== //
export default function SearchPublicNoticeTable({ searchCriteria }) {
@@ -94,16 +95,16 @@ export default function SearchPublicNoticeTable({ searchCriteria }) {
{
id: 'contactPerson',
field: 'contactPerson',
- headerName: 'Client',
+ headerName: 'Client / Payment Method',
sortable: false,
minWidth: 250,
flex: 2,
renderCell: (params) => {
let company = params.row.enCompanyName != null ? params.row.enCompanyName : params.row.chCompanyName;
company = company != null ? company : "";
-
+ let paymentMethod = params.row.paymentMethod!=null?intl.formatMessage({ id: utils.getPaymentMethod(params.row.paymentMethod)}):""
return (<>
- {params?.value}
{company}
+ {params?.value}
{company}
{paymentMethod}
>);
}
},
diff --git a/src/routes/GLDUserRoutes.js b/src/routes/GLDUserRoutes.js
index 39c1b59..53dcfc7 100644
--- a/src/routes/GLDUserRoutes.js
+++ b/src/routes/GLDUserRoutes.js
@@ -16,6 +16,7 @@ const ProofReply_GLD = Loadable(lazy(() => import('pages/Proof/Reply_GLD')));
const PaymentSearch_GLD = Loadable(lazy(() => import('pages/Payment/Search_GLD')));
const PaymentDetails_GLD = Loadable(lazy(() => import('pages/Payment/Details_GLD')));
const DemandNote_Create = Loadable(lazy(() => import('pages/DemandNote/Create')));
+const DemandNote_Export = Loadable(lazy(() => import('pages/DemandNote/Export')));
const DemandNote_Search = Loadable(lazy(() => import('pages/DemandNote/Search')));
const DemandNote_Details = Loadable(lazy(() => import('pages/DemandNote/Details')));
const GFMIS_Search = Loadable(lazy(() => import('pages/GFMIS')));
@@ -90,6 +91,12 @@ const GLDUserRoutes = {
element:
}:{},
+ isGranted(["MAINTAIN_DEMANDNOTE"])?
+ {
+ path: '/paymentPage/exportGDN',
+ element:
+ }:{},
+
isGrantedAny(["VIEW_DEMANDNOTE","MAINTAIN_DEMANDNOTE"])?
{
path: '/paymentPage/demandNote',
diff --git a/src/translations/en.json b/src/translations/en.json
index e48f270..1706d33 100644
--- a/src/translations/en.json
+++ b/src/translations/en.json
@@ -428,7 +428,7 @@
"post":"By Post",
"cheque":"Cheque",
"cash":"Cash",
- "paymentMethod":"Payment Method",
+ "paymentMethodAndDeadLine":"Payment Method / DeadLine",
"payOnlineMethod":"Online",
"payDnMethod":"Demand Note",
"payNPGOMethod":"NPGO Collection Office",
diff --git a/src/translations/zh-CN.json b/src/translations/zh-CN.json
index 663db84..f38b859 100644
--- a/src/translations/zh-CN.json
+++ b/src/translations/zh-CN.json
@@ -57,7 +57,7 @@
"post":"通过邮寄",
"cheque":"支票",
"cash":"现金",
- "paymentMethod":"付款方式",
+ "paymentMethodAndDeadLine":"付款方式/期限",
"payOnlineMethod":"网上支付",
"payDnMethod":"缴款单支付",
"payNPGOMethod":"收款办公室付款",
diff --git a/src/translations/zh-HK.json b/src/translations/zh-HK.json
index 2440c08..14a4646 100644
--- a/src/translations/zh-HK.json
+++ b/src/translations/zh-HK.json
@@ -57,7 +57,7 @@
"post":"透過郵寄",
"cheque":"支票",
"cash":"現金",
- "paymentMethod":"付款方式",
+ "paymentMethodAndDeadLine":"付款方式/期限",
"payOnlineMethod":"網上支付",
"payDnMethod":"繳款單支付",
"payNPGOMethod":"收款辦公室付款",
diff --git a/src/utils/ApiPathConst.js b/src/utils/ApiPathConst.js
index 6ab9a82..8531d3a 100644
--- a/src/utils/ApiPathConst.js
+++ b/src/utils/ApiPathConst.js
@@ -168,6 +168,10 @@ export const DEMAND_NOTE_MARK_PAID = apiPath+'/demandNote/mark-as-paid';//POST
export const DEMAND_NOTE_ATTACH = apiPath+'/demandNote/attach';//POST
export const DEMAND_NOTE_EXPORT = apiPath+'/demandNote/export';//POST
+export const GDN_VIEW = apiPath+'/application/list-Demand-Notice';//GET
+export const GDN_EXPORT = apiPath+'/application/export';//GET
+
+
export const GFIMIS_LIST = apiPath+'/gfmis/list';//GET