This commit is contained in:
=
2025-09-02 16:36:29 +08:00
8 changed files with 173 additions and 9 deletions
@@ -1,20 +1,37 @@
package com.budwk.app.zhgh.activity.declarereimbursement.declare.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.lang.Dict;
import cn.hutool.core.util.StrUtil;
import cn.hutool.json.JSONUtil;
import com.budwk.app.base.annotation.SLog;
import com.budwk.app.base.constant.BpmProcessConstant;
import com.budwk.app.base.constant.RoleConstant;
import com.budwk.app.base.exception.BaseException;
import com.budwk.app.base.page.Pagination;
import com.budwk.app.base.result.Result;
import com.budwk.app.base.utils.CommonDownloadUtil;
import com.budwk.app.base.utils.PageUtil;
import com.budwk.app.base.utils.SysOfficeTemplateUtil;
import com.budwk.app.bpm.vo.BpmTaskApprovalRecordVo;
import com.budwk.app.flow.engine.FlowEngine;
import com.budwk.app.flow.entity.ProcessInstance;
import com.budwk.app.flow.entity.ProcessTask;
import com.budwk.app.flow.vo.ProcessTaskVO;
import com.budwk.app.web.commons.auth.utils.AuthUtil;
import com.budwk.app.web.commons.auth.utils.SecurityUtil;
import com.budwk.app.web.commons.base.Globals;
import com.budwk.app.zhgh.activity.declarereimbursement.declare.models.ActivityDeclareInfo;
import com.budwk.app.zhgh.activity.declarereimbursement.declare.service.ActivityDeclareService;
import com.budwk.app.zhgh.activity.declarereimbursement.reimbursement.models.ActivityReimbursementInfo;
import com.budwk.app.zhgh.activity.declarereimbursement.vo.ActivityBudgetVO;
import com.budwk.app.zhgh.activity.declarereimbursement.vo.CommonPageParam;
import com.deepoove.poi.XWPFTemplate;
import com.deepoove.poi.config.Configure;
import com.deepoove.poi.plugin.table.LoopRowTableRenderPolicy;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.nutz.aop.interceptor.ioc.TransAop;
import org.nutz.dao.Cnd;
import org.nutz.dao.Dao;
@@ -28,7 +45,11 @@ import org.nutz.lang.util.NutMap;
import org.nutz.mvc.annotation.At;
import org.nutz.mvc.annotation.Ok;
import javax.servlet.http.HttpServletResponse;
import javax.validation.Valid;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.util.*;
/**
* @version 1.0
@@ -37,6 +58,7 @@ import javax.validation.Valid;
* @Date 2025/8/26 10:14
* @注释
*/
@Slf4j
@IocBean
@Ok("json")
@ApiOperation("我的活动申报")
@@ -48,6 +70,8 @@ public class ActivityDeclareMineController {
@Inject
private FlowEngine flowEngine;
@Inject
private SysOfficeTemplateUtil sysOfficeTemplateUtil;
@Inject
private ActivityDeclareService activityDeclareService;
@At("")
@@ -132,7 +156,7 @@ public class ActivityDeclareMineController {
@At
@ApiOperation("删除活动申报")
@Aop(TransAop.READ_COMMITTED)
@SaCheckPermission("member.apply.submit")
@SaCheckPermission("activityDeclare.mine")
@SLog(tag = "活动申报", msg = "删除活动申报id: ${args[0]}")
public Result onDelete(@Valid String id) {
dao.clear(ActivityDeclareInfo.class, Cnd.where("id", "=", id));
@@ -149,4 +173,125 @@ public class ActivityDeclareMineController {
return Result.success();
}
@At
@Ok("void")
@SaCheckPermission("activityDeclare.mine")
@SLog(tag = "活动申报", msg = "导出活动申报表")
public void doExport(@Valid String id, HttpServletResponse response) {
HashMap<String, Object> docData = new HashMap<>();
Sql sql = Sqls.create("""
SELECT
info.*,
ins.id AS instanceId
FROM
`activity_declare_info` info
LEFT JOIN wf_process_instance ins ON ins.businessNo = info.id
WHERE
ins.state = 20 AND info.id = @id
""").setParam("id", id);
sql.setCallback(Sqls.callback.map());
dao.execute(sql);
NutMap info = (NutMap) sql.getResult();
String activityContent = info.getString("activityContent");
info.put("activityContent", sysOfficeTemplateUtil.convertRichTextToDocText(activityContent));
docData.put("schoolName", Globals.AppName);
docData.put("info", info);
List<ProcessTaskVO> doneTaskVos = new ArrayList<>();
List<ProcessTask> doneTaskList = flowEngine.processTaskService().getDoneTaskList(info.getLong("instanceId"), null);
for (ProcessTask doneTask : doneTaskList) {
ProcessTaskVO taskVO = flowEngine.processTaskService().findById(doneTask.getId());
doneTaskVos.add(taskVO);
}
// 分工会审核
doneTaskVos.stream().filter(task -> "分工会审核".equals(task.getDisplayName()))
.max(Comparator.comparing(ProcessTaskVO::getCreatedAt))
.ifPresent(v -> {
Dict taskFormData = v.getTaskFormData();
HashMap<String, Object> approval = new HashMap<>();
approval.put("date", DateUtil.format(v.getFinishTime(), "yyyy年MM月dd日"));
approval.put("user", taskFormData.getStr("tf_userName"));
if (StrUtil.isNotBlank(taskFormData.getStr("tf_sign"))) {
approval.put("sign", sysOfficeTemplateUtil.createPictureRenderData(taskFormData.getStr("tf_sign")));
}
approval.put("opinion", taskFormData.getStr("tf_opinion"));
docData.put("fgh", approval);
});
// 协会负责人审核
doneTaskVos.stream().filter(task -> "协会负责人审核".equals(task.getDisplayName()))
.max(Comparator.comparing(ProcessTaskVO::getCreatedAt))
.ifPresent(v -> {
Dict taskFormData = v.getTaskFormData();
HashMap<String, Object> approval = new HashMap<>();
approval.put("date", DateUtil.format(v.getFinishTime(), "yyyy年MM月dd日"));
approval.put("user", taskFormData.getStr("tf_userName"));
if (StrUtil.isNotBlank(taskFormData.getStr("tf_sign"))) {
approval.put("sign", sysOfficeTemplateUtil.createPictureRenderData(taskFormData.getStr("tf_sign")));
}
approval.put("opinion", taskFormData.getStr("tf_opinion"));
docData.put("xh", approval);
});
// 校工会负责人审核
doneTaskVos.stream().filter(task -> "校工会负责人审核".equals(task.getDisplayName()))
.max(Comparator.comparing(ProcessTaskVO::getCreatedAt))
.ifPresent(v -> {
Dict taskFormData = v.getTaskFormData();
HashMap<String, Object> approval = new HashMap<>();
approval.put("date", DateUtil.format(v.getFinishTime(), "yyyy年MM月dd日"));
approval.put("user", taskFormData.getStr("tf_userName"));
if (StrUtil.isNotBlank(taskFormData.getStr("tf_sign"))) {
approval.put("sign", sysOfficeTemplateUtil.createPictureRenderData(taskFormData.getStr("tf_sign")));
}
approval.put("opinion", taskFormData.getStr("tf_opinion"));
docData.put("xfzr", approval);
});
// 校工会主席审核
doneTaskVos.stream().filter(task -> "校工会主席审核".equals(task.getDisplayName()))
.max(Comparator.comparing(ProcessTaskVO::getCreatedAt))
.ifPresent(v -> {
Dict taskFormData = v.getTaskFormData();
HashMap<String, Object> approval = new HashMap<>();
approval.put("date", DateUtil.format(v.getFinishTime(), "yyyy年MM月dd日"));
approval.put("user", taskFormData.getStr("tf_userName"));
if (StrUtil.isNotBlank(taskFormData.getStr("tf_sign"))) {
approval.put("sign", sysOfficeTemplateUtil.createPictureRenderData(taskFormData.getStr("tf_sign")));
}
approval.put("opinion", taskFormData.getStr("tf_opinion"));
docData.put("xzx", approval);
});
String budgetsStr = info.getString("budgets");
List<ActivityBudgetVO> list = JSONUtil.parseArray(budgetsStr).toList(ActivityBudgetVO.class);
for (int i = 0; i < list.size(); i++) {
list.get(i).setRanking(i + 1);
}
docData.put("budgets", list);
LoopRowTableRenderPolicy policy = new LoopRowTableRenderPolicy();
Configure config = Configure.builder()
.bind("budgets", policy)
.build();
String fileName = Globals.AppName + "" + info.getString("activityName") + "】申报表.docx";
try (ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream()) {
XWPFTemplate.compile(sysOfficeTemplateUtil.getTemplate("activity_declare"), config).render(docData).writeAndClose(byteArrayOutputStream);
CommonDownloadUtil.download(fileName, byteArrayOutputStream.toByteArray(), response);
} catch (IOException e) {
log.error("活动申报表导出失败,id:{},错误信息:{}", id, e.getMessage());
}
}
}
@@ -86,7 +86,7 @@ public class ActivityReimbursementApplyController {
double sum = activityReimbursementInfo.getBudgets().stream()
.mapToDouble(v -> ObjectUtil.defaultIfNull(v.getActualPrice(), 0D))
.sum();
activityReimbursementInfo.setBudgetMoney(new BigDecimal(sum));
activityReimbursementInfo.setActualMoney(new BigDecimal(sum));
dao.insertOrUpdate(activityReimbursementInfo);
return Result.success();
}
@@ -106,14 +106,15 @@ public class ActivityReimbursementApplyController {
double sum = activityReimbursementInfo.getBudgets().stream()
.mapToDouble(v -> ObjectUtil.defaultIfNull(v.getActualPrice(), 0D))
.sum();
activityReimbursementInfo.setBudgetMoney(new BigDecimal(sum));
activityReimbursementInfo.setActualMoney(new BigDecimal(sum));
dao.insertOrUpdate(activityReimbursementInfo);
// 开启流程实例
Dict args = Dict.create();
args.set(FlowConst.SUBMIT_TYPE, ProcessSubmitTypeEnum.APPLY.getCode());
args.set(FlowConst.FORM_DATA, activityReimbursementInfo);
ProcessInstance instance = flowEngine.startProcessInstanceByKey("HDSB", activityReimbursementInfo.getId(), SecurityUtil.getUserId(), args);
args.set("type", activityReimbursementInfo.getActivityType());
ProcessInstance instance = flowEngine.startProcessInstanceByKey("HDBX", activityReimbursementInfo.getId(), SecurityUtil.getUserId(), args);
// 自动完成第一个申请任务
List<ProcessTask> doingTaskList = flowEngine.processTaskService().getDoingTaskList(instance.getId(), null);
@@ -138,7 +139,7 @@ public class ActivityReimbursementApplyController {
double sum = activityReimbursementInfo.getBudgets().stream()
.mapToDouble(v -> ObjectUtil.defaultIfNull(v.getActualPrice(), 0D))
.sum();
activityReimbursementInfo.setBudgetMoney(new BigDecimal(sum));
activityReimbursementInfo.setActualMoney(new BigDecimal(sum));
dao.insertOrUpdate(activityReimbursementInfo);
Dict dict = Dict.create();
@@ -26,6 +26,7 @@ import org.nutz.lang.util.NutMap;
import org.nutz.mvc.annotation.At;
import org.nutz.mvc.annotation.Ok;
import javax.servlet.http.HttpServletResponse;
import javax.validation.Valid;
/**
@@ -135,5 +136,4 @@ public class ActivityReimbursementMineController {
flowEngine.processInstanceService().deleteProcessInstanceByBusinessKey(id);
return Result.success();
}
}
@@ -15,6 +15,8 @@ import lombok.Data;
@ApiModel("费用预算")
public class ActivityBudgetVO {
private Integer ranking;
@ApiModelProperty(value = "名称")
private String name;
@@ -51,10 +51,10 @@ public class CommonPageParam extends PageForm<ActivityDeclareInfo> {
RoleConstant.BRANCH_UNION_ADMIN.name(),
RoleConstant.BRANCH_UNION_OPERATOR.name())) {
cnd.and(prefix + "unionid", "=", SecurityUtil.getUnionId());
}
if (AuthUtil.hasRoleOr(RoleConstant.CLUB_MANAGER.name(), RoleConstant.CLUB_PRESIDENT.name())) {
} else if (AuthUtil.hasRoleOr(RoleConstant.CLUB_MANAGER.name(), RoleConstant.CLUB_PRESIDENT.name())) {
// cnd.and(prefix + "clubId", "=", );
} else {
cnd.andEX(prefix + "userId", "=", SecurityUtil.getUserId());
}
} else {
cnd.andEX(prefix + "unionId", "=", this.getUnionId());
@@ -92,6 +92,8 @@ layout("/layouts/platform.html"){
<el-button v-if="row.canRevoke" @click="onRevoke(row)" size="mini" type="danger">撤回
</el-button>
<el-button v-if="row.taskKey === 'startTask' || !row.instanceId" @click="onDelete(row.id)" size="mini" type="danger">删除</el-button>
<el-button v-if="row.instanceState === 20" @click="doExport(row)" size="mini" type="primary">导出</el-button>
</template>
</el-table-column>
</el-table>
@@ -141,6 +143,9 @@ layout("/layouts/platform.html"){
'info': INFO
},
methods: {
doExport(row){
this.$downLoad('/platform/activityDeclare/mine/doExport?id=' + row.id)
},
onApply() {
window.location.href = '/platform/activityDeclare/apply'
},
@@ -1,6 +1,11 @@
<!--#
layout("/layouts/platform.html"){
#-->
<style>
.el-descriptions-item__label {
width: 15% !important;
}
</style>
<div id="app">
<div>
<el-card shadow="never">
@@ -92,6 +92,8 @@ layout("/layouts/platform.html"){
<el-button v-if="row.canRevoke" @click="onRevoke(row)" size="mini" type="danger">撤回
</el-button>
<el-button v-if="row.taskKey === 'startTask' || !row.instanceId" @click="onDelete(row.id)" size="mini" type="danger">删除</el-button>
<el-button @click="doExport(row)">导出</el-button>
</template>
</el-table-column>
</el-table>
@@ -140,6 +142,10 @@ layout("/layouts/platform.html"){
'info': INFO
},
methods: {
// 导出示例
doExport(row){
this.$downLoad('/platform/activityDeclare/mine?id=' + row.declareId)
},
onApply() {
window.location.href = '/platform/activityReimbursement/apply'
},