diff --git a/api/app/lib/controllers/report/achievement.js b/api/app/lib/controllers/report/achievement.js
index 9a027ef..80090f3 100644
--- a/api/app/lib/controllers/report/achievement.js
+++ b/api/app/lib/controllers/report/achievement.js
@@ -283,8 +283,36 @@ async function getContractDetail(ctx) {
ctx.body = { name: 'FindError', message: '查询合同明细表数据失败' }
}
}
+
+/**
+ * 查询开票明细表数据
+ * @param {*} ctx ctx ctx.query:{keywordTarget-关键字项、keyword-关键字内容、limit-页宽, page-页码}
+ */
+async function getInvoicingDetail(ctx) {
+ try {
+ const { models } = ctx.fs.dc;
+ const { keywordTarget, keyword, limit, page } = ctx.query;
+ const where = {};
+ if (keywordTarget && keyword) {
+ where[keywordTarget] = { $iLike: `%${keyword}%` };
+ }
+ let invoiceDetail = await models.InvoiceDetail.findAndCountAll({
+ where: where,
+ offset: Number(page) * Number(limit),
+ limit: Number(limit),
+ order: [['id', 'DESC']]
+ });
+ ctx.status = 200
+ ctx.body = invoiceDetail;
+ } catch (error) {
+ ctx.fs.logger.error(`path:${ctx.path},error:${error}`)
+ ctx.status = 400;
+ ctx.body = { name: 'FindError', message: '查询开票明细表数据失败' }
+ }
+}
module.exports = {
getReceivedDetail,//回款
getAchievementDetail,//业绩
getContractDetail,
+ getInvoicingDetail
}
\ No newline at end of file
diff --git a/api/app/lib/routes/report/index.js b/api/app/lib/routes/report/index.js
index b986cd6..59cab38 100644
--- a/api/app/lib/routes/report/index.js
+++ b/api/app/lib/routes/report/index.js
@@ -18,4 +18,7 @@ module.exports = function (app, router, opts) {
app.fs.api.logAttr['GET/contract/detail'] = { content: '查询合同明细表', visible: false };
router.get('/contract/detail', achieve.getContractDetail);
+
+ app.fs.api.logAttr['GET/invoicing/detail'] = { content: '查询开票明细表', visible: false };
+ router.get('/invoicing/detail', achieve.getInvoicingDetail);
};
\ No newline at end of file
diff --git a/web/client/src/sections/business/actions/achievement-report.js b/web/client/src/sections/business/actions/achievement-report.js
index b7d5e94..3bc785b 100644
--- a/web/client/src/sections/business/actions/achievement-report.js
+++ b/web/client/src/sections/business/actions/achievement-report.js
@@ -39,4 +39,17 @@ export function getContractDetail(query) {
msg: { option: "查询合同明细表" },
reducer: { name: "ContractDetail", params: { noClear: true } },
});
+}
+
+//查询开票明细表
+export function getInvoicingDetail(query) {
+ return (dispatch) => basicAction({
+ type: "get",
+ dispatch: dispatch,
+ actionType: "GET_INVOICING_DETAIL",
+ query: query,
+ url: `${ApiTable.getInvoicingDetail}`,
+ msg: { option: "查询开票明细表" },
+ reducer: { name: "InvoicingDetail", params: { noClear: true } },
+ });
}
\ No newline at end of file
diff --git a/web/client/src/sections/business/containers/performanceReport/contractDetails.jsx b/web/client/src/sections/business/containers/performanceReport/contractDetails.jsx
index b7a379b..ba5c6c5 100644
--- a/web/client/src/sections/business/containers/performanceReport/contractDetails.jsx
+++ b/web/client/src/sections/business/containers/performanceReport/contractDetails.jsx
@@ -23,6 +23,7 @@ const ContractDetails = (props) => {
const [exportUrl, setExportUrl] = useState('');
const page = useRef(query.page);
+ const scroll = useMemo(() => ({}), []);
const CONTRACTDETAILS = "contractDetails";
const renderColumns = (columnKeys) => {
@@ -108,7 +109,6 @@ const ContractDetails = (props) => {
}
})
}
- const scroll = useMemo(() => ({}), []);
return (
<>
@@ -160,9 +160,10 @@ const ContractDetails = (props) => {
onClick={() => { setImportModalV(true); }}>
导入
- {
- exportAllData()
- }}>
+
{
+ exportAllData()
+ }}>
导出全部
diff --git a/web/client/src/sections/business/containers/performanceReport/invoicingDetails.jsx b/web/client/src/sections/business/containers/performanceReport/invoicingDetails.jsx
index 91c1fe3..851ae5c 100644
--- a/web/client/src/sections/business/containers/performanceReport/invoicingDetails.jsx
+++ b/web/client/src/sections/business/containers/performanceReport/invoicingDetails.jsx
@@ -1,6 +1,6 @@
import React, { useEffect, useState, useRef, useMemo } from 'react';
import { connect } from 'react-redux';
-import { Select, Input, Button, Table, Pagination, Skeleton } from '@douyinfe/semi-ui';
+import { Select, Input, Button, Table, Pagination, Skeleton, Toast, } from '@douyinfe/semi-ui';
import { SkeletonScreen, Setup } from "$components";
import { IconSearch } from '@douyinfe/semi-icons';
import ImportInvoicingDetailsModal from './importInvoicingDetailsModal';
@@ -10,7 +10,7 @@ import moment from 'moment'
const InvoicingDetails = (props) => {
const { dispatch, actions } = props
- const { } = actions;
+ const { businessManagement } = actions;
const [keywordTarget, setKeywordTarget] = useState('contractNo');
const [keyword, setKeyword] = useState('');//搜索内容
const [limits, setLimits] = useState()//每页实际条数
@@ -20,6 +20,11 @@ const InvoicingDetails = (props) => {
const [setup, setSetup] = useState(false);//表格设置是否显现
const [setupp, setSetupp] = useState([]);//实际显示的表格列表
+
+ const [exportUrl, setExportUrl] = useState('');
+ const page = useRef(query.page);
+ const scroll = useMemo(() => ({}), []);
+
const INVOICINGDETAILS = "invoicingDetails";
const renderColumns = (columnKeys) => {
let columns = [];
@@ -52,6 +57,7 @@ const InvoicingDetails = (props) => {
)
: "";
attribute();
+ getInvoicingDetailData();
}, []);
//获取表格属性设置
function attribute() {
@@ -66,9 +72,16 @@ const InvoicingDetails = (props) => {
}
setSetupp(newColumns);
}
- useEffect(() => {
- }, [query])
+ function getInvoicingDetailData(param) {
+ let queryParam = param || query;
+ dispatch(businessManagement.getInvoicingDetail({ keywordTarget, keyword, ...queryParam })).then(r => {
+ if (r.success) {
+ setTableData(r.payload?.data?.rows);
+ setLimits(r.payload?.data?.count);
+ }
+ })
+ }
function handleRow(record, index) {// 给偶数行设置斑马纹
if (index % 2 === 0) {
return {
@@ -80,7 +93,22 @@ const InvoicingDetails = (props) => {
return {};
}
}
- const scroll = useMemo(() => ({}), []);
+
+ const exportAllData = () => {
+ dispatch(businessManagement.getInvoicingDetail({ limit: 1, page: 0 })).then((res) => {
+ if (res.success) {
+ if (res.payload.data.count) {
+ let url = `export/invoicing/detail?token=${user.token}×tamp=${moment().valueOf()}`
+ setExportUrl(url);
+ } else {
+ Toast.info({
+ content: '暂无可导出的数据',
+ duration: 3,
+ })
+ }
+ }
+ })
+ }
return (
<>
@@ -120,6 +148,7 @@ const InvoicingDetails = (props) => {
@@ -130,7 +159,10 @@ const InvoicingDetails = (props) => {
onClick={() => { setImportModalV(true); }}>
导入
-
+
{
+ exportAllData()
+ }}>
导出全部
@@ -185,20 +217,25 @@ const InvoicingDetails = (props) => {
setImportModalV(false);
}} /> : ''
}
+ {
+ exportUrl ? : ''
+ }
- {setup ? (
- {
- setSetup(false);
- attribute();
- }}
- />
- ) : (
- ""
- )}
+ {
+ setup ? (
+ {
+ setSetup(false);
+ attribute();
+ }}
+ />
+ ) : (
+ ""
+ )
+ }
>
)
}
diff --git a/web/client/src/utils/webapi.js b/web/client/src/utils/webapi.js
index cad4b9b..56519c5 100644
--- a/web/client/src/utils/webapi.js
+++ b/web/client/src/utils/webapi.js
@@ -24,10 +24,11 @@ export const ApiTable = {
getReceivedDetail: 'detail/received/back',
getAchievementDetail: 'detail/achievement',
getContractDetail: 'contract/detail',
+ getInvoicingDetail: 'invoicing/detail',
};
export const RouteTable = {
- apiRoot: "/api/root",
- fileUpload: "/_upload/new",
- cleanUpUploadTrash: "/_upload/cleanup",
- getServiceUrl: '/_service/url'
+ apiRoot: "/api/root",
+ fileUpload: "/_upload/new",
+ cleanUpUploadTrash: "/_upload/cleanup",
+ getServiceUrl: '/_service/url'
};