diff --git a/api/app/lib/controllers/attendance/index.js b/api/app/lib/controllers/attendance/index.js index 96eb2cb..5e6af8a 100644 --- a/api/app/lib/controllers/attendance/index.js +++ b/api/app/lib/controllers/attendance/index.js @@ -205,10 +205,14 @@ async function vacateStatistic(ctx) { startDate, endDate, pepUserIds }) + const remarkList = await models.VacateRemark.findAll({}); //查询备注 + returnD.forEach(u => { let vacateStatistic = sumRes.filter(s => s.pepUserId == u.pepUserId) + let remarkData = remarkList.filter(e => e.pepUserId == u.pepUserId) u.vacateDuration = vacateStatistic.reduce((sum, vs) => sum + vs.duration, 0) u.vacateStatistic = vacateStatistic + u.remark = remarkData.length ? remarkData[0].remark : null }) ctx.status = 200; ctx.body = { @@ -255,6 +259,8 @@ async function exportVacateStatistic(ctx) { startDate, endDate, pepUserIds }) + const remarkList = await models.VacateRemark.findAll({}); //查询备注 + returnD.forEach(u => { u.departmrnt = u.departmrnt.map(dep => dep.name).join('、') u.role = u.role.map(r => r.name).join('、') @@ -269,6 +275,9 @@ async function exportVacateStatistic(ctx) { }, 0) } u.vacateDayStatisticDuration = (u.vacateDayStatisticDuration || 0) / 3600 + u.userActiveStatus = u.userActiveStatus == 1 ? '在职' : u.userActiveStatus == 2 ? '离职' : '特殊状态-特殊账号' + let remarkData = remarkList.filter(e => e.pepUserId == u.pepUserId) + u.remark = remarkData.length ? (remarkData[0].remark == '' ? '无' : remarkData[0].remark) : '无' }) const header = [{ @@ -283,6 +292,9 @@ async function exportVacateStatistic(ctx) { }, { title: '职位', key: 'role', + }, { + title: '在职状态', + key: 'userActiveStatus', },] .concat(vacateTypeRes.map(v => { return { @@ -302,6 +314,12 @@ async function exportVacateStatistic(ctx) { defaultValue: '0', }] ) + .concat( + [{ + title: '备注', + key: 'remark', + }] + ) const fileName = `请假统计_${startDate ? moment(startDate).format('YYYY-MM-DD') : ''}${startDate && endDate ? '-' : ''}${endDate ? moment(endDate).format('YYYY-MM-DD') : ''}${startDate || endDate ? '_' : ''}${moment().format('YYYYMMDDHHmmss')}` + '.csv' const filePath = await simpleExcelDown({ data: returnD, header, fileName: fileName }) @@ -320,10 +338,34 @@ async function exportVacateStatistic(ctx) { } } +// 添加请假统计备注 +async function vacateRemark(ctx) { + try { + const { models } = ctx.fs.dc; + const { remark, pepUserId } = ctx.query; + let oldData = await models.VacateRemark.findOne({ where: { pepUserId: pepUserId } }); + if (oldData) { + await models.VacateRemark.update({ remark, pepUserId }, { where: { pepUserId: pepUserId } }); + } else { + await models.VacateRemark.create({ remark, pepUserId }); + } + + ctx.status = 200; + ctx.body = '添加备注成功'; + } catch (error) { + ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); + ctx.status = 400; + ctx.body = { + "message": "添加备注失败" + } + } +} + module.exports = { overtimeStatistic, exportOvertimeStatistic, vacateType, vacateStatistic, exportVacateStatistic, + vacateRemark }; \ No newline at end of file diff --git a/api/app/lib/models/vacate_remark.js b/api/app/lib/models/vacate_remark.js new file mode 100644 index 0000000..0e5e823 --- /dev/null +++ b/api/app/lib/models/vacate_remark.js @@ -0,0 +1,43 @@ +/* eslint-disable*/ +'use strict'; + +module.exports = dc => { + const DataTypes = dc.ORM; + const sequelize = dc.orm; + const VacateRemark = sequelize.define("vacateRemark", { + id: { + type: DataTypes.INTEGER, + allowNull: false, + defaultValue: null, + comment: null, + primaryKey: true, + field: "id", + autoIncrement: true, + unique: "vacate_remark_id_uindex" + }, + pepUserId: { + type: DataTypes.INTEGER, + allowNull: false, + defaultValue: null, + comment: 'pep用户id', + primaryKey: false, + field: "pep_user_id", + autoIncrement: false + }, + remark: { + type: DataTypes.TEXT, + allowNull: true, + defaultValue: null, + comment: '备注', + primaryKey: false, + field: "remark", + autoIncrement: false + } + }, { + tableName: "vacate_remark", + comment: "", + indexes: [] + }); + dc.models.VacateRemark = VacateRemark; + return VacateRemark; +}; \ No newline at end of file diff --git a/api/app/lib/routes/attendance/index.js b/api/app/lib/routes/attendance/index.js index cefea8e..d19093c 100644 --- a/api/app/lib/routes/attendance/index.js +++ b/api/app/lib/routes/attendance/index.js @@ -17,4 +17,7 @@ module.exports = function (app, router, opts) { app.fs.api.logAttr['GET/attendance/vacate/export'] = { content: '请假统计导出', visible: true }; router.get('/attendance/vacate/export', attendance.exportVacateStatistic); + + app.fs.api.logAttr['PUT/attendance/vacate/creat/remark'] = { content: '添加请假统计备注', visible: true }; + router.put('/attendance/vacate/creat/remark', attendance.vacateRemark); }; \ No newline at end of file diff --git a/web/client/src/sections/humanAffairs/actions/index.js b/web/client/src/sections/humanAffairs/actions/index.js index b1869a8..858e5ec 100644 --- a/web/client/src/sections/humanAffairs/actions/index.js +++ b/web/client/src/sections/humanAffairs/actions/index.js @@ -8,6 +8,7 @@ import * as personalTrainRecord from './personalTrainRecord' import * as resourceRepository from './resourceRepository' import * as employeeCommunication from './employeeCommunication' import * as employeeAssessment from './employeeAssessment' +import * as vacateRemark from './vacateRemark' export default { ...personnelFiles, @@ -17,5 +18,6 @@ export default { ...personalTrainRecord, ...resourceRepository, ...employeeCommunication, - ...employeeAssessment + ...employeeAssessment, + ...vacateRemark } \ No newline at end of file diff --git a/web/client/src/sections/humanAffairs/actions/vacateRemark.js b/web/client/src/sections/humanAffairs/actions/vacateRemark.js new file mode 100644 index 0000000..2634ced --- /dev/null +++ b/web/client/src/sections/humanAffairs/actions/vacateRemark.js @@ -0,0 +1,15 @@ +'use strict'; + +import { ApiTable, basicAction } from '$utils' + +export function createVacateRemark(query) {//添加请假统计备注 + return (dispatch) => basicAction({ + type: "put", + dispatch: dispatch, + query: query, + actionType: "PUT_VACATE_REMARK", + url: `${ApiTable.createVacateRemark}`, + msg: { option: '添加备注' }, + reducer: {}, + }); +} \ No newline at end of file diff --git a/web/client/src/sections/humanAffairs/containers/leaveStatistics.jsx b/web/client/src/sections/humanAffairs/containers/leaveStatistics.jsx index aba7d84..e987d70 100644 --- a/web/client/src/sections/humanAffairs/containers/leaveStatistics.jsx +++ b/web/client/src/sections/humanAffairs/containers/leaveStatistics.jsx @@ -1,6 +1,7 @@ import React, { useEffect, useState, useRef, useMemo } from 'react'; import { connect } from 'react-redux'; import { Table, Button, Pagination, Skeleton, Form, Tooltip } from '@douyinfe/semi-ui'; +import VacateRemark from './vacateRemark'; import { IconSearch } from '@douyinfe/semi-icons'; import { SkeletonScreen } from "$components"; import '../style.less' @@ -26,6 +27,8 @@ const leaveStatistics = (props) => { const [downloadUrl, setDownloadUrl] = useState('')//下载pdf const LEAVESTATISTICS = "leaveStatistics"; const page = useRef(query.page);//哪一页 + const [modalV, setModalV] = useState(false); + const [remark, setRemark] = useState(null); const [tableList, setTableList] = useState([{ title: '展示信息', @@ -255,7 +258,11 @@ const leaveStatistics = (props) => { dataIndex: "remark", key: "remark", render: (_, r, index) => { - // return (r.vacateCount ? r.vacateCount : '0') + return ( + r.remark?.length > 22 ? + {r.remark.slice(0, 21) + '...'} + : (r.remark ? r.remark : '无') + ) }, }) column.push({ @@ -266,7 +273,10 @@ const leaveStatistics = (props) => { render: (_, r, index) => { return (
- 添加备注 + { + setModalV(true); + setRemark({ pepUserId: r.pepUserId, remark: r.remark }) + }}>添加备注
) }, @@ -292,6 +302,11 @@ const leaveStatistics = (props) => { } } const scroll = useMemo(() => ({}), []); + + const closeAndFetch = () => { + setModalV(false) + getAttendanceVacateList(); + } return ( <>
@@ -454,6 +469,13 @@ const leaveStatistics = (props) => {
+ + { + modalV ? closeAndFetch()} + onCancel={() => setModalV(false)} /> : '' + } {setup ? ( { + const { dispatch, actions, onCancel, close, remarkData } = props; + console.log(actions, 'actionsactionsactions'); + const { humanAffairs } = actions; + const form = useRef();//表单 + //初始化 + useEffect(() => { }, []); + + function handleOk() { + form.current.validate().then((values) => { + dispatch(humanAffairs.createVacateRemark({ pepUserId: remarkData.pepUserId, remark: values.remark || '' })).then((res) => { + if (res.success) { + close(); + } + }) + }) + } + + return ( + +
(form.current = formApi)} labelPosition={'left'}> + + +
+ ) +} + +function mapStateToProps(state) { + const { global } = state; + return { + actions: global.actions, + }; +} + +export default connect(mapStateToProps)(VacateRemark); \ No newline at end of file diff --git a/web/client/src/utils/webapi.js b/web/client/src/utils/webapi.js index 3995a99..699b70e 100644 --- a/web/client/src/utils/webapi.js +++ b/web/client/src/utils/webapi.js @@ -64,7 +64,10 @@ export const ApiTable = { getEmployeeCommunicate: 'employee/communicate/list', //考核 - getemployeeAssessmentList: 'employessAssessment/list/{type}' + getemployeeAssessmentList: 'employessAssessment/list/{type}', + + // 请假统计添加备注 + createVacateRemark: 'attendance/vacate/creat/remark' }; export const RouteTable = {