xiongzhu hace 5 años
padre
commit
6349dcf86c

+ 39 - 0
src/main/java/com/x1ongzhu/wisFactory/domain/HolidaySetting.java

@@ -0,0 +1,39 @@
+package com.x1ongzhu.wisFactory.domain;
+
+import com.alibaba.excel.annotation.ExcelIgnore;
+import com.x1ongzhu.wisFactory.enums.HolidayType;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.AllArgsConstructor;
+import lombok.Builder;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import javax.persistence.*;
+import java.time.LocalDate;
+import java.util.List;
+
+@Data
+@Entity
+@AllArgsConstructor
+@NoArgsConstructor
+@Builder
+@ApiModel("节假日设置")
+public class HolidaySetting extends BaseEntity {
+    @ManyToMany(fetch = FetchType.LAZY, cascade = {CascadeType.DETACH})
+    @JoinTable(
+            name = "department_holiday",
+            joinColumns = {@JoinColumn(name = "holiday_id", referencedColumnName = "id", foreignKey = @ForeignKey(ConstraintMode.NO_CONSTRAINT))},
+            inverseJoinColumns = {@JoinColumn(name = "department_id", referencedColumnName = "id", foreignKey = @ForeignKey(name = "none", value = ConstraintMode.NO_CONSTRAINT))})
+    @OrderBy("id")
+    private List<Department> departments;
+
+    private LocalDate start;
+
+    private LocalDate end;
+
+    @Enumerated(EnumType.STRING)
+    private HolidayType type;
+
+    private String remark;
+}

+ 12 - 3
src/main/java/com/x1ongzhu/wisFactory/dto/StaffAttendanceBrief.java

@@ -32,10 +32,10 @@ public class StaffAttendanceBrief {
     @ExcelProperty("总天数")
     private int totalDays;
 
-    @ExcelProperty("工作日")
+    @ExcelProperty("应出勤")
     private int workDays;
 
-    @ExcelProperty("到勤天数")
+    @ExcelProperty("实际出勤")
     private int attendDays;
 
     @ExcelProperty("缺勤天数")
@@ -68,9 +68,18 @@ public class StaffAttendanceBrief {
     @ExcelProperty("加班天数")
     private int overtime;
 
-    @ExcelProperty("加班时长")
+    @ExcelProperty("加班时长")
     private double overtimeHours;
 
+    @ExcelProperty("工作日加班时长")
+    private double overtimeHours1;
+
+    @ExcelProperty("休息日加班时长")
+    private double overtimeHours2;
+
+    @ExcelProperty("节假日加班时长")
+    private double overtimeHours3;
+
     @ExcelProperty("加班详情")
     private String overtimeDetail;
 

+ 3 - 0
src/main/java/com/x1ongzhu/wisFactory/dto/StaffAttendanceDetail.java

@@ -56,4 +56,7 @@ public class StaffAttendanceDetail {
     @ExcelProperty("说明")
     private String remark;
 
+    private boolean restDay;
+
+    private boolean holiday;
 }

+ 15 - 0
src/main/java/com/x1ongzhu/wisFactory/enums/HolidayType.java

@@ -0,0 +1,15 @@
+package com.x1ongzhu.wisFactory.enums;
+
+public enum HolidayType {
+    WORK("工作日"),
+    HOLIDAY("节假日");
+    private final String description;
+
+    HolidayType(String description) {
+        this.description = description;
+    }
+
+    public String getDescription() {
+        return description;
+    }
+}

+ 11 - 0
src/main/java/com/x1ongzhu/wisFactory/repo/HolidaySettingRepo.java

@@ -0,0 +1,11 @@
+package com.x1ongzhu.wisFactory.repo;
+
+import com.x1ongzhu.wisFactory.domain.Department;
+import com.x1ongzhu.wisFactory.domain.HolidaySetting;
+import org.springframework.data.jpa.repository.JpaRepository;
+import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
+
+import java.util.List;
+
+public interface HolidaySettingRepo extends JpaRepository<HolidaySetting, Long>, JpaSpecificationExecutor<HolidaySetting> {
+}

+ 39 - 5
src/main/java/com/x1ongzhu/wisFactory/service/AttendanceService.java

@@ -6,6 +6,7 @@ import com.x1ongzhu.wisFactory.dto.StaffAccessDTO;
 import com.x1ongzhu.wisFactory.dto.StaffAttendanceBrief;
 import com.x1ongzhu.wisFactory.dto.StaffAttendanceDetail;
 import com.x1ongzhu.wisFactory.enums.AttendanceType;
+import com.x1ongzhu.wisFactory.enums.HolidayType;
 import com.x1ongzhu.wisFactory.exception.BusinessException;
 import com.x1ongzhu.wisFactory.repo.*;
 import com.x1ongzhu.wisFactory.utils.DateTimeUtils;
@@ -14,9 +15,14 @@ import lombok.Data;
 import lombok.extern.slf4j.Slf4j;
 import org.apache.commons.collections.list.SynchronizedList;
 import org.apache.commons.lang3.StringUtils;
+import org.springframework.data.jpa.domain.Specification;
 import org.springframework.scheduling.annotation.Scheduled;
 import org.springframework.stereotype.Service;
 
+import javax.persistence.criteria.CriteriaBuilder;
+import javax.persistence.criteria.CriteriaQuery;
+import javax.persistence.criteria.Predicate;
+import javax.persistence.criteria.Root;
 import java.math.BigDecimal;
 import java.math.RoundingMode;
 import java.time.LocalDate;
@@ -33,11 +39,12 @@ import java.util.stream.Stream;
 @Slf4j
 public class AttendanceService {
 
-    private AttendanceRepo   attendanceRepo;
-    private StaffAccessRepo  staffAccessRepo;
-    private StaffInfoRepo    staffInfoRepo;
-    private SysConfigService sysConfigService;
-    private DepartmentRepo   departmentRepo;
+    private AttendanceRepo     attendanceRepo;
+    private StaffAccessRepo    staffAccessRepo;
+    private StaffInfoRepo      staffInfoRepo;
+    private SysConfigService   sysConfigService;
+    private DepartmentRepo     departmentRepo;
+    private HolidaySettingRepo holidaySettingRepo;
 
     //    @Scheduled(cron = "0 0 1 * * ?")
     public void autoGenAttendance() {
@@ -334,6 +341,13 @@ public class AttendanceService {
             log.error("department null: staffid {}", staffInfo.getId());
         }
         department = departmentRepo.findById(department.getId()).orElseThrow(new BusinessException("部门不存在"));
+        Department finalDepartment = department;
+        List<HolidaySetting> holidaySettings = holidaySettingRepo
+                .findAll((Specification<HolidaySetting>) (root, criteriaQuery, criteriaBuilder) ->
+                        criteriaQuery.where(criteriaBuilder.greaterThanOrEqualTo(root.get("end"), start),
+                                criteriaBuilder.lessThanOrEqualTo(root.get("start"), end),
+                                criteriaBuilder.isMember(finalDepartment, root.get("departments")))
+                                .getRestriction());
         List<StaffAccess> accessList = staffAccessRepo
                 .findByEmployNoAndAccessTimeBetweenOrderByAccessTimeAsc(staffInfo.getEmployNo(),
                         start.atStartOfDay(), end.atTime(Constants.TIME_MAX));
@@ -358,8 +372,21 @@ public class AttendanceService {
         for (int i = 0; i < brief.getTotalDays(); i++) {
             LocalDate date = start.plusDays(i);
             boolean restDay = !workDay.contains(date.getDayOfWeek().getValue());
+            boolean holiday = false;
+            HolidaySetting setting = holidaySettings.stream().filter(holidaySetting -> {
+                return date.compareTo(holidaySetting.getStart()) >= 0 && date.compareTo(holidaySetting.getEnd()) <= 0;
+            }).findFirst().orElse(null);
+            if (setting != null) {
+                if (setting.getType() == HolidayType.HOLIDAY) {
+                    holiday = true;
+                } else if (setting.getType() == HolidayType.WORK) {
+                    restDay = false;
+                }
+            }
             StaffAttendanceDetail detail = calc(staffInfo, accessList, date, department, restDay);
             if (detail != null) {
+                detail.setRestDay(restDay);
+                detail.setHoliday(holiday);
                 staffAttendanceDetailList.add(detail);
                 brief.setHours(brief.getHours() + detail.getHours());
                 if (detail.isAbsent()) {
@@ -381,6 +408,13 @@ public class AttendanceService {
                     if (detail.getOvertime() > 0) {
                         brief.setOvertime(brief.getOvertime() + 1);
                         brief.setOvertimeHours(brief.getOvertimeHours() + detail.getOvertime());
+                        if (holiday) {
+                            brief.setOvertimeHours3(brief.getOvertimeHours3() + detail.getOvertime());
+                        } else if (restDay) {
+                            brief.setOvertimeHours2(brief.getOvertimeHours2() + detail.getOvertime());
+                        } else {
+                            brief.setOvertimeHours1(brief.getOvertimeHours1() + detail.getOvertime());
+                        }
                         brief.addOvertimeDetail(DateTimeUtils.format(date, "yyyy-MM-dd") + "  " + detail
                                 .getOvertime() + "小时");
                     }

+ 14 - 0
src/main/java/com/x1ongzhu/wisFactory/service/HolidaySettingService.java

@@ -0,0 +1,14 @@
+package com.x1ongzhu.wisFactory.service;
+
+import com.x1ongzhu.wisFactory.domain.HolidaySetting;
+import com.x1ongzhu.wisFactory.repo.HolidaySettingRepo;
+import lombok.AllArgsConstructor;
+import org.springframework.stereotype.Service;
+
+@Service
+@AllArgsConstructor
+public class HolidaySettingService {
+
+    private HolidaySettingRepo holidaySettingRepo;
+
+}

+ 19 - 0
src/main/java/com/x1ongzhu/wisFactory/web/AttendanceController.java

@@ -2,8 +2,11 @@ package com.x1ongzhu.wisFactory.web;
 
 import com.alibaba.excel.EasyExcel;
 import com.alibaba.excel.ExcelWriter;
+import com.alibaba.excel.write.handler.WriteHandler;
 import com.alibaba.excel.write.metadata.WriteSheet;
 import com.alibaba.excel.write.metadata.WriteTable;
+import com.alibaba.excel.write.metadata.style.WriteCellStyle;
+import com.alibaba.excel.write.style.HorizontalCellStyleStrategy;
 import com.x1ongzhu.wisFactory.domain.Attendance;
 import com.x1ongzhu.wisFactory.dto.StaffAttendanceBrief;
 import com.x1ongzhu.wisFactory.dto.PageQuery;
@@ -17,6 +20,8 @@ import com.x1ongzhu.wisFactory.utils.excel.ExcelUtils;
 import com.x1ongzhu.wisFactory.utils.excel.LocalDateConverter;
 import com.x1ongzhu.wisFactory.utils.excel.LocalDateTimeConverter;
 import lombok.AllArgsConstructor;
+import org.apache.poi.ss.usermodel.FillPatternType;
+import org.apache.poi.ss.usermodel.IndexedColors;
 import org.springframework.data.domain.Page;
 import org.springframework.web.bind.annotation.*;
 
@@ -26,6 +31,7 @@ import java.time.LocalDate;
 import java.util.Collections;
 import java.util.List;
 import java.util.Map;
+import java.util.stream.Collectors;
 
 @RestController
 @RequestMapping("/attendance")
@@ -120,9 +126,22 @@ public class AttendanceController extends BaseController {
                     .needHead(Boolean.FALSE)
                     .build();
             // 这里必须指定需要头,table 会继承sheet的配置,sheet配置了不需要,table 默认也是不需要
+            WriteCellStyle headStyle = new WriteCellStyle();
+            List<WriteCellStyle> contentStyle = brief.getDetails().stream().map(detail -> {
+                WriteCellStyle style = new WriteCellStyle();
+                if (detail.isHoliday()) {
+                    style.setFillPatternType(FillPatternType.SOLID_FOREGROUND);
+                    style.setFillForegroundColor(IndexedColors.LIGHT_TURQUOISE.getIndex());
+                } else if (detail.isRestDay()) {
+                    style.setFillPatternType(FillPatternType.SOLID_FOREGROUND);
+                    style.setFillForegroundColor(IndexedColors.LIGHT_YELLOW.getIndex());
+                }
+                return style;
+            }).collect(Collectors.toList());
             WriteTable writeTable0 = EasyExcel.writerTable(0)
                     .head(StaffAttendanceDetail.class)
                     .needHead(Boolean.TRUE)
+                    .registerWriteHandler(new HorizontalCellStyleStrategy(headStyle, contentStyle))
                     .build();
             WriteTable writeTable1 = EasyExcel.writerTable(1)
                     .head(StaffAttendanceBrief.class)

+ 60 - 0
src/main/java/com/x1ongzhu/wisFactory/web/HolidaySettingController.java

@@ -0,0 +1,60 @@
+package com.x1ongzhu.wisFactory.web;
+import com.x1ongzhu.wisFactory.domain.HolidaySetting;
+import com.x1ongzhu.wisFactory.service.HolidaySettingService;
+import com.x1ongzhu.wisFactory.dto.PageQuery;
+import com.x1ongzhu.wisFactory.exception.BusinessException;
+import com.x1ongzhu.wisFactory.repo.HolidaySettingRepo;
+import com.x1ongzhu.wisFactory.utils.ObjUtils;
+import com.x1ongzhu.wisFactory.utils.excel.ExcelUtils;
+import lombok.AllArgsConstructor;
+import org.springframework.data.domain.Page;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.web.bind.annotation.*;
+
+import javax.servlet.http.HttpServletResponse;
+import java.io.IOException;
+import java.util.List;
+
+@RestController
+@RequestMapping("/holidaySetting")
+@AllArgsConstructor
+public class HolidaySettingController extends BaseController {
+    private HolidaySettingService holidaySettingService;
+    private HolidaySettingRepo holidaySettingRepo;
+
+    //@PreAuthorize("hasRole('ADMIN')")
+    @PostMapping("/save")
+    public HolidaySetting save(@RequestBody HolidaySetting record) {
+        if (record.getId() != null) {
+            HolidaySetting orig = holidaySettingRepo.findById(record.getId()).orElseThrow(new BusinessException("无记录"));
+            ObjUtils.merge(orig, record);
+            return holidaySettingRepo.save(orig);
+        }
+        return holidaySettingRepo.save(record);
+    }
+
+
+    //@PreAuthorize("hasRole('ADMIN')")
+    @GetMapping("/all")
+    public Page<HolidaySetting> all(PageQuery pageQuery) {
+        return holidaySettingRepo.findAll(toSpecification(pageQuery,HolidaySetting.class), toPageRequest(pageQuery));
+    }
+
+    @GetMapping("/get/{id}")
+    public HolidaySetting get(@PathVariable Long id) {
+        return holidaySettingRepo.findById(id).orElseThrow(new BusinessException("无记录"));
+    }
+
+    @PostMapping("/del/{id}")
+    public void del(@PathVariable Long id) {
+        holidaySettingRepo.deleteById(id);
+    }
+
+    @GetMapping("/excel")
+    @ResponseBody
+    public void excel(HttpServletResponse response, PageQuery pageQuery) throws IOException {
+        List<HolidaySetting> data = all(pageQuery).getContent();
+        ExcelUtils.export(response, data);
+    }
+}
+

+ 1 - 0
src/main/resources/genjson/HolidaySetting.json

@@ -0,0 +1 @@
+{"tableName":"HolidaySetting","className":"HolidaySetting","remark":"节假日管理","genTable":true,"genClass":true,"genList":true,"genForm":true,"genRouter":true,"javaPath":"/Users/drew/Projects/Java/shdq-factory/src/main/java/com/x1ongzhu/wisFactory","viewPath":"/Users/drew/Projects/Java/shdq-factory/src/main/vue/src/views","routerPath":"/Users/drew/Projects/Java/shdq-factory/src/main/vue/src","resourcesPath":"/Users/drew/Projects/Java/shdq-factory/src/main/resources","dataBaseType":"Mysql","fields":[{"name":"start","modelName":"start","remark":"start","showInList":true,"showInForm":true,"formType":"date"},{"name":"end","modelName":"end","remark":"end","showInList":true,"showInForm":true,"formType":"date"},{"name":"departments","modelName":"departments","remark":"departments","showInList":true,"showInForm":true,"formType":"singleLineText"},{"name":"type","modelName":"type","remark":"type","showInList":true,"showInForm":true,"formType":"select","apiFlag":"1","optionsValue":"[{\"label\":\"工作日\",\"value\":\"WORK\"},{\"label\":\"节假日\",\"value\":\"HOLIDAY\"}]"}],"readTable":false,"dataSourceCode":"dataSource","genJson":"","subtables":[],"update":false,"basePackage":"com.x1ongzhu.wisFactory","tablePackage":"com.x1ongzhu.wisFactory.domain.HolidaySetting"}

+ 18 - 0
src/main/vue/src/router.js

@@ -342,6 +342,24 @@ const router = new Router({
                     meta: {
                         title: '时长配置'
                     }
+                },
+                {
+                    path: '/holidaySettingEdit',
+                    name: 'HolidaySettingEdit',
+                    component: () =>
+                        import(/* webpackChunkName: "holidaySettingEdit" */ '@/views/HolidaySettingEdit.vue'),
+                    meta: {
+                        title: '节假日管理编辑'
+                    }
+                },
+                {
+                    path: '/holidaySettingList',
+                    name: 'HolidaySettingList',
+                    component: () =>
+                        import(/* webpackChunkName: "holidaySettingList" */ '@/views/HolidaySettingList.vue'),
+                    meta: {
+                        title: '节假日管理'
+                    }
                 }
                 /**INSERT_LOCATION**/
             ]

+ 77 - 0
src/main/vue/src/views/HolidaySettingEdit.vue

@@ -0,0 +1,77 @@
+<template>
+    <div class="edit-view"></div>
+</template>
+<script>
+export default {
+    name: 'HolidaySettingEdit',
+    created() {
+        if (this.$route.query.id) {
+            this.$http
+                .get('holidaySetting/get/' + this.$route.query.id)
+                .then(res => {
+                    this.formData = res;
+                })
+                .catch(e => {
+                    console.log(e);
+                    this.$message.error(e.error);
+                });
+        }
+    },
+    data() {
+        return {
+            saving: false,
+            formData: {},
+            rules: {},
+            typeOptions: [
+                { label: '工作日', value: 'WORK' },
+                { label: '节假日', value: 'HOLIDAY' }
+            ]
+        };
+    },
+    methods: {
+        onSave() {
+            this.$refs.form.validate(valid => {
+                if (valid) {
+                    this.submit();
+                } else {
+                    return false;
+                }
+            });
+        },
+        submit() {
+            let data = { ...this.formData };
+
+            this.saving = true;
+            this.$http
+                .post('/holidaySetting/save', data, { body: 'json' })
+                .then(res => {
+                    this.saving = false;
+                    this.$message.success('成功');
+                    this.$router.go(-1);
+                })
+                .catch(e => {
+                    console.log(e);
+                    this.saving = false;
+                    this.$message.error(e.error);
+                });
+        },
+        onDelete() {
+            this.$alert('删除将无法恢复,确认要删除么?', '警告', { type: 'error' })
+                .then(() => {
+                    return this.$http.post(`/holidaySetting/del/${this.formData.id}`);
+                })
+                .then(() => {
+                    this.$message.success('删除成功');
+                    this.$router.go(-1);
+                })
+                .catch(e => {
+                    if (e !== 'cancel') {
+                        console.log(e);
+                        this.$message.error(e.error);
+                    }
+                });
+        }
+    }
+};
+</script>
+<style lang="less" scoped></style>

+ 313 - 0
src/main/vue/src/views/HolidaySettingList.vue

@@ -0,0 +1,313 @@
+<template>
+    <div class="list-view">
+        <div class="filters-container">
+            <el-input placeholder="输入关键字" v-model="search" clearable class="filter-item"></el-input>
+            <el-button @click="getData" type="primary" icon="el-icon-search" class="filter-item">搜索 </el-button>
+            <el-button @click="addRow" type="primary" icon="el-icon-plus" class="filter-item">添加 </el-button>
+            <el-button
+                @click="download"
+                type="primary"
+                icon="el-icon-download"
+                :loading="downloading"
+                class="filter-item"
+                >导出EXCEL
+            </el-button>
+        </div>
+        <el-table
+            :data="tableData"
+            row-key="id"
+            ref="table"
+            header-row-class-name="table-header-row"
+            header-cell-class-name="table-header-cell"
+            row-class-name="table-row"
+            cell-class-name="table-cell"
+            :height="tableHeight"
+        >
+            <el-table-column v-if="multipleMode" align="center" type="selection" width="50"> </el-table-column>
+            <el-table-column prop="id" label="ID" width="100"> </el-table-column>
+            <el-table-column prop="start" label="开始日期"> </el-table-column>
+            <el-table-column prop="end" label="结束日期"> </el-table-column>
+            <el-table-column prop="departments" label="部门" :formatter="departmentFormatter" show-overflow-tooltip>
+            </el-table-column>
+            <el-table-column prop="type" label="类型" :formatter="typeFormatter"> </el-table-column>
+            <el-table-column prop="remark" label="备注"></el-table-column>
+            <el-table-column label="操作" align="center" fixed="right" min-width="100">
+                <template slot-scope="{ row }">
+                    <el-button @click="deleteRow(row)" type="danger" size="mini" plain>删除</el-button>
+                </template>
+            </el-table-column>
+        </el-table>
+        <div class="pagination-wrapper">
+            <!-- <div class="multiple-mode-wrapper">
+                <el-button v-if="!multipleMode" @click="toggleMultipleMode(true)">批量编辑</el-button>
+                <el-button-group v-else>
+                    <el-button @click="operation1">批量操作1</el-button>
+                    <el-button @click="operation2">批量操作2</el-button>
+                    <el-button @click="toggleMultipleMode(false)">取消</el-button>
+                </el-button-group>
+            </div> -->
+            <el-pagination
+                background
+                @size-change="onSizeChange"
+                @current-change="onCurrentChange"
+                :current-page="page"
+                :page-sizes="[10, 20, 30, 40, 50]"
+                :page-size="pageSize"
+                layout="total, sizes, prev, pager, next, jumper"
+                :total="totalElements"
+            >
+            </el-pagination>
+        </div>
+
+        <el-dialog :visible.sync="showEditDialog" width="600px">
+            <el-form
+                :model="formData"
+                :rules="rules"
+                ref="form"
+                label-width="108px"
+                label-position="right"
+                size="small"
+            >
+                <el-form-item prop="start" label="开始日期">
+                    <el-date-picker
+                        v-model="formData.start"
+                        type="date"
+                        value-format="yyyy-MM-dd"
+                        placeholder="选择日期"
+                    >
+                    </el-date-picker>
+                </el-form-item>
+                <el-form-item prop="end" label="结束日期">
+                    <el-date-picker v-model="formData.end" type="date" value-format="yyyy-MM-dd" placeholder="选择日期">
+                    </el-date-picker>
+                </el-form-item>
+                <el-form-item prop="departments" label="部门">
+                    <div class="department-select">
+                        <el-checkbox :indeterminate="isIndeterminate" v-model="checkAll" @change="handleCheckAllChange">
+                            全选
+                        </el-checkbox>
+                        <el-checkbox-group v-model="formData.departments" @change="handleCheckedDepartmentsChange">
+                            <el-checkbox v-for="item in departments" :label="item" :key="item.id">
+                                {{ item.name }}
+                            </el-checkbox>
+                        </el-checkbox-group>
+                    </div>
+                </el-form-item>
+                <el-form-item prop="type" label="类型">
+                    <el-select v-model="formData.type" clearable filterable placeholder="请选择">
+                        <el-option
+                            v-for="item in typeOptions"
+                            :key="item.value"
+                            :label="item.label"
+                            :value="item.value"
+                        >
+                        </el-option>
+                    </el-select>
+                </el-form-item>
+                <el-form-item prop="remark" label="备注">
+                    <el-input v-model="formData.remark"></el-input>
+                </el-form-item>
+            </el-form>
+            <div slot="footer">
+                <el-button @click="onSave" :loading="saving" type="primary">保存</el-button>
+                <el-button @click="showEditDialog = false">取消</el-button>
+            </div>
+        </el-dialog>
+    </div>
+</template>
+<script>
+import { mapState } from 'vuex';
+import pageableTable from '@/mixins/pageableTable';
+import { isBefore, parse, format } from 'date-fns';
+export default {
+    name: 'HolidaySettingList',
+    mixins: [pageableTable],
+    data() {
+        return {
+            multipleMode: false,
+            search: '',
+            url: '/holidaySetting/all',
+            downloading: false,
+            typeOptions: [
+                { label: '节假日', value: 'HOLIDAY' },
+                { label: '工作日', value: 'WORK' }
+            ],
+            formData: {
+                departments: []
+            },
+            rules: {
+                start: { required: true, message: '请选择开始日期' },
+                end: [
+                    { required: true, message: '请选择结束日期' },
+                    {
+                        validator: (rule, value, callback) => {
+                            if (value && this.formData.start) {
+                                if (
+                                    isBefore(
+                                        parse(value, 'yyyy-MM-dd', new Date()),
+                                        parse(this.formData.start, 'yyyy-MM-dd', new Date())
+                                    )
+                                ) {
+                                    callback(new Error('结束日期不能早于开始日期'));
+                                    return;
+                                }
+                            }
+                            callback();
+                        },
+                        trigger: 'blur'
+                    }
+                ],
+                departments: [{ required: true, message: '请选择部门', trigger: 'blur' }],
+                type: { required: true, message: '请选择类型' }
+            },
+            departments: [],
+            checkAll: false,
+            isIndeterminate: true,
+            showEditDialog: false,
+            saving: false,
+            sortStr: 'createdAt,desc'
+        };
+    },
+    computed: {
+        selection() {
+            return this.$refs.table.selection.map(i => i.id);
+        }
+    },
+    created() {
+        this.$http.get('/department/all', { size: 1000 }).then(res => {
+            this.departments = res.content;
+        });
+    },
+    methods: {
+        typeFormatter(row, column, cellValue, index) {
+            let selectedOption = this.typeOptions.find(i => i.value === cellValue);
+            if (selectedOption) {
+                return selectedOption.label;
+            }
+            return '';
+        },
+        beforeGetData() {
+            if (this.search) {
+                return { search: this.search };
+            }
+        },
+        toggleMultipleMode(multipleMode) {
+            this.multipleMode = multipleMode;
+            if (!multipleMode) {
+                this.$refs.table.clearSelection();
+            }
+        },
+        addRow() {
+            this.formData = {
+                departments: []
+            };
+            if (this.$refs.form) {
+                this.$refs.form.clearValidate();
+            }
+            this.showEditDialog = true;
+        },
+        editRow(row) {
+            this.$router.push({
+                path: '/holidaySettingEdit',
+                query: {
+                    id: row.id
+                }
+            });
+        },
+        download() {
+            this.downloading = true;
+            this.$axios
+                .get('/holidaySetting/excel', {
+                    responseType: 'blob',
+                    params: { size: 10000 }
+                })
+                .then(res => {
+                    console.log(res);
+                    this.downloading = false;
+                    const downloadUrl = window.URL.createObjectURL(new Blob([res.data]));
+                    const link = document.createElement('a');
+                    link.href = downloadUrl;
+                    link.setAttribute('download', res.headers['content-disposition'].split('filename=')[1]);
+                    document.body.appendChild(link);
+                    link.click();
+                    link.remove();
+                })
+                .catch(e => {
+                    console.log(e);
+                    this.downloading = false;
+                    this.$message.error(e.error);
+                });
+        },
+        onSave() {
+            this.$refs.form.validate(valid => {
+                if (valid) {
+                    this.submit();
+                } else {
+                    return false;
+                }
+            });
+        },
+        submit() {
+            let data = { ...this.formData };
+
+            this.saving = true;
+            this.$http
+                .post('/holidaySetting/save', data, { body: 'json' })
+                .then(res => {
+                    this.saving = false;
+                    this.showEditDialog = false;
+                    this.$message.success('成功');
+                    this.getData();
+                })
+                .catch(e => {
+                    console.log(e);
+                    this.saving = false;
+                    this.$message.error(e.error);
+                });
+        },
+        deleteRow(row) {
+            this.$alert('删除将无法恢复,确认要删除么?', '警告', { type: 'error' })
+                .then(() => {
+                    return this.$http.post(`/holidaySetting/del/${row.id}`);
+                })
+                .then(() => {
+                    this.$message.success('删除成功');
+                    this.getData();
+                })
+                .catch(e => {
+                    if (e !== 'cancel') {
+                        this.$message.error(e.error);
+                    }
+                });
+        },
+        handleCheckAllChange(val) {
+            this.formData.departments = val ? this.departments : [];
+            this.isIndeterminate = false;
+        },
+        handleCheckedDepartmentsChange(value) {
+            let checkedCount = value.length;
+            this.checkAll = checkedCount === this.departments.length;
+            this.isIndeterminate = checkedCount > 0 && checkedCount < this.departments.length;
+        },
+        departmentFormatter(row, column, value, index) {
+            if (value) {
+                return value.map(i => i.name).join('\n');
+            }
+            return '';
+        }
+    }
+};
+</script>
+<style lang="less" scoped>
+.department-select {
+    height: 300px;
+    overflow: auto;
+    border-radius: 4px;
+    border: 1px solid #dcdfe6;
+    padding: 0 15px;
+    margin-right: 20px;
+    .el-checkbox {
+        display: block;
+    }
+}
+</style>