Browse Source

流程优化

home 2 years ago
parent
commit
4f02885dd7
37 changed files with 1593 additions and 414 deletions
  1. 1 1
      bladex/blade-service-api/blade-user-api/src/main/java/org/springblade/system/user/feign/IUserClient.java
  2. 2 2
      bladex/blade-service/blade-user/src/main/java/org/springblade/system/user/feign/UserClient.java
  3. 170 170
      bladex/blade-service/blade-user/src/main/java/org/springblade/system/user/service/IUserService.java
  4. 2 2
      bladex/blade-service/blade-user/src/main/java/org/springblade/system/user/service/impl/UserServiceImpl.java
  5. 11 0
      hx-common/common-tool/src/main/java/com/fjhx/utils/Assert.java
  6. 0 2
      hx-common/service-flow/src/main/java/com/fjhx/controller/example/ExampleInfoController.java
  7. 226 40
      hx-common/service-flow/src/main/java/com/fjhx/feign/FlowClient.java
  8. 3 2
      hx-common/service-flow/src/main/java/com/fjhx/service/example/impl/ExampleInfoServiceImpl.java
  9. 64 33
      hx-common/service-flow/src/main/java/com/fjhx/service/process/impl/ProcessNodeButtonServiceImpl.java
  10. 5 0
      hx-service-api/service-flow-api/src/main/java/com/fjhx/constants/FlowExplainConstant.java
  11. 5 0
      hx-service-api/service-flow-api/src/main/java/com/fjhx/entity/example/ExampleInfo.java
  12. 5 0
      hx-service-api/service-flow-api/src/main/java/com/fjhx/entity/process/ProcessNodeButton.java
  13. 43 0
      hx-service-api/service-flow-api/src/main/java/com/fjhx/enums/HandleResultEnum.java
  14. 29 5
      hx-service-api/service-flow-api/src/main/java/com/fjhx/feign/IFlowClient.java
  15. 6 1
      hx-service-api/service-flow-api/src/main/java/com/fjhx/params/ExampleResult.java
  16. 48 0
      hx-service-api/service-flow-api/src/main/java/com/fjhx/params/JumpVo.java
  17. 2 2
      hx-service-api/service-flow-api/src/main/java/com/fjhx/utils/ExampleAbstract.java
  18. 1 1
      hx-service-api/service-flow-api/src/main/java/com/fjhx/utils/FlowConstructor.java
  19. 103 133
      hx-service-api/service-flow-api/src/main/java/com/fjhx/utils/FlowConstructorBack.java
  20. 57 0
      hx-service-api/storage-api/src/main/java/com/fjhx/entity/stock/StockBackPlan.java
  21. 91 0
      hx-service-api/storage-api/src/main/java/com/fjhx/entity/stock/StockBackPlanDetails.java
  22. 17 0
      hx-service-api/storage-api/src/main/java/com/fjhx/params/stock/StockBackPlanDetailsEx.java
  23. 17 0
      hx-service-api/storage-api/src/main/java/com/fjhx/params/stock/StockBackPlanDetailsVo.java
  24. 17 0
      hx-service-api/storage-api/src/main/java/com/fjhx/params/stock/StockBackPlanEx.java
  25. 17 0
      hx-service-api/storage-api/src/main/java/com/fjhx/params/stock/StockBackPlanVo.java
  26. 5 5
      hx-service/storage/src/main/java/com/fjhx/applet/mapper/MaterialReceiveMapper.xml
  27. 17 15
      hx-service/storage/src/main/java/com/fjhx/applet/service/impl/MaterialReceiveServiceImpl.java
  28. 34 0
      hx-service/storage/src/main/java/com/fjhx/stock/controller/StockBackPlanController.java
  29. 56 0
      hx-service/storage/src/main/java/com/fjhx/stock/controller/StockBackPlanDetailsController.java
  30. 16 0
      hx-service/storage/src/main/java/com/fjhx/stock/mapper/StockBackPlanDetailsMapper.java
  31. 5 0
      hx-service/storage/src/main/java/com/fjhx/stock/mapper/StockBackPlanDetailsMapper.xml
  32. 35 0
      hx-service/storage/src/main/java/com/fjhx/stock/mapper/StockBackPlanMapper.java
  33. 56 0
      hx-service/storage/src/main/java/com/fjhx/stock/mapper/StockBackPlanMapper.xml
  34. 28 0
      hx-service/storage/src/main/java/com/fjhx/stock/service/StockBackPlanDetailsService.java
  35. 20 0
      hx-service/storage/src/main/java/com/fjhx/stock/service/StockBackPlanService.java
  36. 54 0
      hx-service/storage/src/main/java/com/fjhx/stock/service/impl/StockBackPlanDetailsServiceImpl.java
  37. 325 0
      hx-service/storage/src/main/java/com/fjhx/stock/service/impl/StockBackPlanServiceImpl.java

+ 1 - 1
bladex/blade-service-api/blade-user-api/src/main/java/org/springblade/system/user/feign/IUserClient.java

@@ -166,7 +166,7 @@ public interface IUserClient {
      * 根据jobNo获取openId
      */
     @GetMapping(GET_OPENID_BY_ACCOUNT)
-    Map<String, String> getOpenidByAccount(@RequestParam("account") List<String> account);
+    Map<String, String> getOpenidByAccount(@RequestParam("account") List<String> account, @RequestParam("tenantId") String tenantId);
 
 
 }

+ 2 - 2
bladex/blade-service/blade-user/src/main/java/org/springblade/system/user/feign/UserClient.java

@@ -120,8 +120,8 @@ public class UserClient implements IUserClient {
 
     @GetMapping(GET_OPENID_BY_ACCOUNT)
     @Override
-    public Map<String, String> getOpenidByAccount(List<String> account) {
-        return service.getOpenidByAccount(account);
+    public Map<String, String> getOpenidByAccount(List<String> account, String tenantId) {
+        return service.getOpenidByAccount(account, tenantId);
     }
 
 }

+ 170 - 170
bladex/blade-service/blade-user/src/main/java/org/springblade/system/user/service/IUserService.java

@@ -38,181 +38,181 @@ import java.util.Map;
  */
 public interface IUserService extends BaseService<User> {
 
-	/**
-	 * 新增用户
-	 *
-	 * @param user
-	 * @return
-	 */
-	boolean submit(User user);
-
-	/**
-	 * 修改用户
-	 *
-	 * @param user
-	 * @return
-	 */
-	boolean updateUser(User user);
-
-	/**
-	 * 修改用户基本信息
-	 *
-	 * @param user
-	 * @return
-	 */
-	boolean updateUserInfo(User user);
-
-	/**
-	 * 自定义分页
-	 *
-	 * @param page
-	 * @param user
-	 * @param deptId
-	 * @param tenantId
-	 * @return
-	 */
-	IPage<User> selectUserPage(IPage<User> page, User user, Long deptId, String tenantId);
-
-	/**
-	 * 自定义分页
-	 *
-	 * @param user
-	 * @param query
-	 * @return
-	 */
-	IPage<UserVO> selectUserSearch(UserVO user, Query query);
-
-
-	/**
-	 * 用户信息
-	 *
-	 * @param userId
-	 * @return
-	 */
-	UserInfo userInfo(Long userId);
-
-	/**
-	 * 用户信息
-	 *
-	 * @param tenantId
-	 * @param account
-	 * @return
-	 */
-	UserInfo userInfo(String tenantId, String account);
-
-	/**
-	 * 用户信息
-	 *
-	 * @param tenantId
-	 * @param account
-	 * @param userEnum
-	 * @return
-	 */
-	UserInfo userInfo(String tenantId, String account, UserEnum userEnum);
-
-	/**
-	 * 用户信息
-	 *
-	 * @param userOauth
-	 * @return
-	 */
-	UserInfo userInfo(UserOauth userOauth);
-
-	/**
-	 * 根据账号获取用户
-	 *
-	 * @param tenantId
-	 * @param account
-	 * @return
-	 */
-	User userByAccount(String tenantId, String account);
-
-	/**
-	 * 给用户设置角色
-	 *
-	 * @param userIds
-	 * @param roleIds
-	 * @return
-	 */
-	boolean grant(String userIds, String roleIds);
-
-	/**
-	 * 初始化密码
-	 *
-	 * @param userIds
-	 * @return
-	 */
-	boolean resetPassword(String userIds);
-
-	/**
-	 * 修改密码
-	 *
-	 * @param userId
-	 * @param oldPassword
-	 * @param newPassword
-	 * @param newPassword1
-	 * @return
-	 */
-	boolean updatePassword(Long userId, String oldPassword, String newPassword, String newPassword1);
-
-	/**
-	 * 删除用户
-	 *
-	 * @param userIds
-	 * @return
-	 */
-	boolean removeUser(String userIds);
-
-	/**
-	 * 导入用户数据
-	 *
-	 * @param data
-	 * @param isCovered
-	 * @return
-	 */
-	void importUser(List<UserExcel> data, Boolean isCovered);
-
-	/**
-	 * 导出用户数据
-	 *
-	 * @param queryWrapper
-	 * @return
-	 */
-	List<UserExcel> exportUser(Wrapper<User> queryWrapper);
-
-	/**
-	 * 注册用户
-	 *
-	 * @param user
-	 * @param oauthId
-	 * @return
-	 */
-	boolean registerGuest(User user, Long oauthId);
-
-	/**
-	 * 配置用户平台
-	 *
-	 * @param userId
-	 * @param userType
-	 * @param userExt
-	 * @return
-	 */
-	boolean updatePlatform(Long userId, Integer userType, String userExt);
-
-	/**
-	 * 用户详细信息
-	 *
-	 * @param user
-	 * @return
-	 */
-	UserVO platformDetail(User user);
+    /**
+     * 新增用户
+     *
+     * @param user
+     * @return
+     */
+    boolean submit(User user);
+
+    /**
+     * 修改用户
+     *
+     * @param user
+     * @return
+     */
+    boolean updateUser(User user);
+
+    /**
+     * 修改用户基本信息
+     *
+     * @param user
+     * @return
+     */
+    boolean updateUserInfo(User user);
+
+    /**
+     * 自定义分页
+     *
+     * @param page
+     * @param user
+     * @param deptId
+     * @param tenantId
+     * @return
+     */
+    IPage<User> selectUserPage(IPage<User> page, User user, Long deptId, String tenantId);
+
+    /**
+     * 自定义分页
+     *
+     * @param user
+     * @param query
+     * @return
+     */
+    IPage<UserVO> selectUserSearch(UserVO user, Query query);
+
+
+    /**
+     * 用户信息
+     *
+     * @param userId
+     * @return
+     */
+    UserInfo userInfo(Long userId);
+
+    /**
+     * 用户信息
+     *
+     * @param tenantId
+     * @param account
+     * @return
+     */
+    UserInfo userInfo(String tenantId, String account);
+
+    /**
+     * 用户信息
+     *
+     * @param tenantId
+     * @param account
+     * @param userEnum
+     * @return
+     */
+    UserInfo userInfo(String tenantId, String account, UserEnum userEnum);
+
+    /**
+     * 用户信息
+     *
+     * @param userOauth
+     * @return
+     */
+    UserInfo userInfo(UserOauth userOauth);
+
+    /**
+     * 根据账号获取用户
+     *
+     * @param tenantId
+     * @param account
+     * @return
+     */
+    User userByAccount(String tenantId, String account);
+
+    /**
+     * 给用户设置角色
+     *
+     * @param userIds
+     * @param roleIds
+     * @return
+     */
+    boolean grant(String userIds, String roleIds);
+
+    /**
+     * 初始化密码
+     *
+     * @param userIds
+     * @return
+     */
+    boolean resetPassword(String userIds);
+
+    /**
+     * 修改密码
+     *
+     * @param userId
+     * @param oldPassword
+     * @param newPassword
+     * @param newPassword1
+     * @return
+     */
+    boolean updatePassword(Long userId, String oldPassword, String newPassword, String newPassword1);
+
+    /**
+     * 删除用户
+     *
+     * @param userIds
+     * @return
+     */
+    boolean removeUser(String userIds);
+
+    /**
+     * 导入用户数据
+     *
+     * @param data
+     * @param isCovered
+     * @return
+     */
+    void importUser(List<UserExcel> data, Boolean isCovered);
+
+    /**
+     * 导出用户数据
+     *
+     * @param queryWrapper
+     * @return
+     */
+    List<UserExcel> exportUser(Wrapper<User> queryWrapper);
+
+    /**
+     * 注册用户
+     *
+     * @param user
+     * @param oauthId
+     * @return
+     */
+    boolean registerGuest(User user, Long oauthId);
+
+    /**
+     * 配置用户平台
+     *
+     * @param userId
+     * @param userType
+     * @param userExt
+     * @return
+     */
+    boolean updatePlatform(Long userId, Integer userType, String userExt);
+
+    /**
+     * 用户详细信息
+     *
+     * @param user
+     * @return
+     */
+    UserVO platformDetail(User user);
 
     void updateUserById(User user);
 
-	User getUserInfoByAppletOpenId(String openId);
+    User getUserInfoByAppletOpenId(String openId);
 
     Map<String, Long> getTenantUserNum(List<String> tenantIdList);
 
-    Map<String, String> getOpenidByAccount(List<String> account);
+    Map<String, String> getOpenidByAccount(List<String> account, String tenantId);
 
 }

+ 2 - 2
bladex/blade-service/blade-user/src/main/java/org/springblade/system/user/service/impl/UserServiceImpl.java

@@ -467,10 +467,10 @@ public class UserServiceImpl extends BaseServiceImpl<UserMapper, User> implement
     }
 
     @Override
-    public Map<String, String> getOpenidByAccount(List<String> account) {
+    public Map<String, String> getOpenidByAccount(List<String> account, String tenantId) {
         List<User> list = list(Wrappers.<User>lambdaQuery()
                 .select(User::getAppletOpenId, User::getAccount)
-                .eq(TenantEntity::getTenantId, AuthUtil.getTenantId())
+                .eq(TenantEntity::getTenantId, tenantId)
                 .in(User::getAccount, account)
         );
 

+ 11 - 0
hx-common/common-tool/src/main/java/com/fjhx/utils/Assert.java

@@ -1,6 +1,7 @@
 package com.fjhx.utils;
 
 import org.springblade.core.log.exception.ServiceException;
+import org.springblade.core.tool.api.R;
 import org.springblade.core.tool.utils.ObjectUtil;
 
 import java.math.BigDecimal;
@@ -8,6 +9,16 @@ import java.math.BigDecimal;
 public class Assert {
 
     /**
+     * 断言client返回成功
+     *
+     * @param r 返回结果集
+     */
+    public static <T> T result(R<T> r) {
+        Assert.eqTrue(r.isSuccess(), r.getMsg());
+        return r.getData();
+    }
+
+    /**
      * 断言为空
      *
      * @param obj    参数

+ 0 - 2
hx-common/service-flow/src/main/java/com/fjhx/controller/example/ExampleInfoController.java

@@ -32,9 +32,7 @@ public class ExampleInfoController {
      */
     @PostMapping("/record")
     public R record(@RequestBody ExampleInfo exampleInfo) {
-
         List<Map<String, Object>> result = exampleInfoService.record(exampleInfo.getFlowLinkNo());
-
         return R.data(result);
     }
 

+ 226 - 40
hx-common/service-flow/src/main/java/com/fjhx/feign/FlowClient.java

@@ -12,24 +12,27 @@ import com.fjhx.entity.process.ProcessInfo;
 import com.fjhx.entity.process.ProcessNodeButton;
 import com.fjhx.entity.process.ProcessTenant;
 import com.fjhx.enums.ButtonNameEnum;
+import com.fjhx.enums.HandleResultEnum;
 import com.fjhx.enums.ProcessNodeTypeEnum;
-import com.fjhx.params.ExampleInfoEx;
-import com.fjhx.params.ExampleResult;
-import com.fjhx.params.FlowInfoVo;
-import com.fjhx.params.GetNodeButtonVo;
+import com.fjhx.params.*;
 import com.fjhx.service.example.ExampleDetailsService;
 import com.fjhx.service.example.ExampleInfoService;
 import com.fjhx.service.process.ProcessInfoService;
 import com.fjhx.service.process.ProcessNodeButtonService;
 import com.fjhx.service.process.ProcessTenantService;
 import com.fjhx.utils.Assert;
+import org.springblade.core.log.exception.ServiceException;
 import org.springblade.core.secure.utils.AuthUtil;
 import org.springblade.core.tool.api.R;
 import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.transaction.annotation.Transactional;
+import org.springframework.web.bind.annotation.GetMapping;
 import org.springframework.web.bind.annotation.PostMapping;
 import org.springframework.web.bind.annotation.RestController;
 
 import java.util.Arrays;
+import java.util.Collections;
+import java.util.List;
 
 @RestController
 public class FlowClient implements IFlowClient {
@@ -137,15 +140,17 @@ public class FlowClient implements IFlowClient {
         return R.data(exampleInfo);
     }
 
+    @Transactional(rollbackFor = Exception.class)
+    @GetMapping(CREATE)
     @Override
     public R<ExampleResult> create(Long flowLinkNo, String code, String nodeCode, String remarks, String cacheData) {
 
         ExampleResult exampleResult = new ExampleResult();
+        exampleResult.setDeleteExample(true);
 
-        int count = exampleInfoService.count(
-                Wrappers.<ExampleInfo>lambdaQuery()
-                        .eq(ExampleInfo::getFlowLinkNo, flowLinkNo)
-                        .eq(ExampleInfo::getComplete, StatusConstant.NO));
+        int count = exampleInfoService.count(Wrappers.<ExampleInfo>lambdaQuery()
+                .eq(ExampleInfo::getFlowLinkNo, flowLinkNo)
+                .eq(ExampleInfo::getComplete, StatusConstant.NO));
 
         Assert.eqZero(count, FlowExplainConstant.EXPLAIN_NOT_EXIST);
 
@@ -165,29 +170,25 @@ public class FlowClient implements IFlowClient {
         exampleInfo.setFlowLinkNo(flowLinkNo);
         exampleInfo.setCacheData(cacheData);
 
+        // 开始流程明细
+        ExampleDetails startExampleDetails = createExampleDetails(
+                exampleInfo.getId(), processInfo.getId(), null, ButtonNameEnum.START.getType());
+        startExampleDetails.setHandleUserId(AuthUtil.getUserId());
+        startExampleDetails.setRemarks(remarks);
+
         // 走默认流程,直接完成
         if (processTenant == null) {
-            exampleInfo.setComplete(StatusConstant.YES);
             exampleInfo.setFlowType(FlowConstant.FLOW_TYPE_DEFAULT);
-            exampleInfo.setProcessNodeCode(FlowConstant.END_CODE);
+            exampleInfoEnd(exampleInfo);
+            exampleInfo.setHandleResult(HandleResultEnum.ADOPT.getType());
             exampleInfoService.save(exampleInfo);
 
-            ExampleDetails startExampleDetails = new ExampleDetails();
-            startExampleDetails.setExampleInfoId(exampleInfo.getId());
-            startExampleDetails.setProcessInfoId(processInfo.getId());
-            startExampleDetails.setNameType(ButtonNameEnum.START.getType());
-            startExampleDetails.setHandleUserId(AuthUtil.getUserId());
-            startExampleDetails.setRemarks(remarks);
-
-            ExampleDetails endExampleDetails = new ExampleDetails();
-            endExampleDetails.setExampleInfoId(exampleInfo.getId());
-            endExampleDetails.setProcessInfoId(processInfo.getId());
-            endExampleDetails.setNameType(ButtonNameEnum.END.getType());
-
-            exampleDetailsService.saveBatch(Arrays.asList(startExampleDetails, endExampleDetails));
+            // 结束流程明细
+            ExampleDetails endExampleDetails = createExampleDetails(
+                    exampleInfo.getId(), processInfo.getId(), null, ButtonNameEnum.END.getType());
 
             // 封装返回值
-            exampleResult.setExampleInfo(exampleInfo);
+            exampleResult.setOldExampleInfo(exampleInfo);
             exampleResult.setExampleDetailsIdList(
                     Arrays.asList(startExampleDetails.getId(), endExampleDetails.getId()));
             exampleResult.setHandleType(ButtonNameEnum.END.getType());
@@ -197,50 +198,235 @@ public class FlowClient implements IFlowClient {
 
         Long processTenantId = processTenant.getId();
         exampleInfo.setFlowType(FlowConstant.FLOW_TYPE_TENANT);
-
         exampleInfo.setProcessTenantId(processTenantId);
 
-        ExampleDetails startExampleDetails = new ExampleDetails();
-        startExampleDetails.setExampleInfoId(exampleInfo.getId());
-        startExampleDetails.setProcessInfoId(processInfo.getId());
+        // 开始节点明细赋值租户流程id
         startExampleDetails.setProcessTenantId(processTenant.getId());
-        startExampleDetails.setNameType(ButtonNameEnum.START.getType());
-        startExampleDetails.setHandleUserId(AuthUtil.getUserId());
-        startExampleDetails.setRemarks(remarks);
+
+        // 获取跳转节点
+        nodeCode = ObjectUtil.isNotEmpty(nodeCode) ? nodeCode : FlowConstant.START_CODE;
+
+        // 如果流程跳转到结束
+        if (FlowConstant.END_CODE.equals(nodeCode)) {
+            exampleInfoEnd(exampleInfo);
+            exampleInfo.setHandleResult(HandleResultEnum.ADOPT.getType());
+            exampleInfoService.save(exampleInfo);
+
+            ExampleDetails endExampleDetails = createExampleDetails(exampleInfo, ButtonNameEnum.END.getType());
+            exampleDetailsService.saveBatch(Arrays.asList(startExampleDetails, endExampleDetails));
+
+            // 返回值
+            exampleResult.setOldExampleInfo(exampleInfo);
+            exampleResult.setCacheDataStr(cacheData);
+            exampleResult.setExampleDetailsIdList(
+                    Arrays.asList(startExampleDetails.getId(), endExampleDetails.getId()));
+            exampleResult.setHandleType(ButtonNameEnum.END.getType());
+
+            return R.data(exampleResult);
+        }
 
         // 查询节点
         ProcessNodeButton processNodeButton = processNodeButtonService.getOne(
                 Wrappers.<ProcessNodeButton>lambdaQuery()
                         .eq(ProcessNodeButton::getProcessTenantId, processTenantId)
-                        .eq(ProcessNodeButton::getProcessNodeCode, ObjectUtil.isNotEmpty(nodeCode) ? nodeCode : FlowConstant.START_CODE));
+                        .eq(ProcessNodeButton::getProcessNodeCode, nodeCode));
+
+        Assert.notEmpty(processNodeButton, FlowExplainConstant.SPECIFY_BRANCH_EMPTY);
 
         // 如果所在节点是开始节点,流转到下一节点,否则所在节点是指定code的节点
         Long jumpNodeId;
+        String jumpNodeCode;
         if (FlowConstant.START_CODE.equals(processNodeButton.getProcessNodeCode())) {
             jumpNodeId = processNodeButton.getJumpNodeId();
+            jumpNodeCode = processNodeButton.getJumpNodeCode();
         } else {
             jumpNodeId = processNodeButton.getProcessNodeId();
+            jumpNodeCode = processNodeButton.getProcessNodeCode();
         }
 
         // 如果流程跳转到结束
-        if (jumpNodeId.equals(FlowConstant.OVER_PROCESS_FLAG)) {
+        if (FlowConstant.END_CODE.equals(jumpNodeCode)) {
 
-            exampleInfo.setComplete(StatusConstant.YES);
+            exampleInfoEnd(exampleInfo);
+            exampleInfo.setHandleResult(HandleResultEnum.ADOPT.getType());
+            exampleInfoService.save(exampleInfo);
 
-            ExampleDetails endExampleDetails = new ExampleDetails();
-            endExampleDetails.setExampleInfoId(exampleInfo.getId());
-            endExampleDetails.setProcessInfoId(processInfo.getId());
-            endExampleDetails.setProcessTenantId(processTenant.getId());
-            endExampleDetails.setNameType(ButtonNameEnum.END.getType());
+            ExampleDetails endExampleDetails = createExampleDetails(exampleInfo, ButtonNameEnum.END.getType());
+
+            exampleDetailsService.saveBatch(Arrays.asList(startExampleDetails, endExampleDetails));
+
+            // 返回值
+            exampleResult.setExampleDetailsIdList(
+                    Arrays.asList(startExampleDetails.getId(), endExampleDetails.getId()));
+            exampleResult.setHandleType(ButtonNameEnum.END.getType());
 
         } else {
             exampleInfo.setComplete(StatusConstant.NO);
             exampleInfo.setProcessNodeId(jumpNodeId);
+            exampleInfo.setProcessNodeCode(jumpNodeCode);
+            exampleInfo.setHandleResult(HandleResultEnum.NOT_START.getType());
+            exampleInfoService.save(exampleInfo);
+
+            exampleDetailsService.save(startExampleDetails);
 
+            // 返回值
+            exampleResult.setExampleDetailsIdList(Collections.singletonList(startExampleDetails.getId()));
         }
 
+        exampleResult.setOldExampleInfo(exampleInfo);
+        exampleResult.setCacheDataStr(cacheData);
+
+        return R.data(exampleResult);
+    }
+
+    @GetMapping(GET_NODE_BUTTON_BY_ID)
+    @Override
+    public R<ProcessNodeButton> getNodeButtonById(Long buttonId) {
+        ProcessNodeButton processNodeButton = processNodeButtonService.getById(buttonId);
+        Assert.notEmpty(processNodeButton, "nodeButton is null");
+
+        return R.data(processNodeButton);
+    }
+
+
+    @Transactional(rollbackFor = Exception.class)
+    @GetMapping(JUMP)
+    @Override
+    public R<ExampleResult> jump(JumpVo jumpVo) {
+
+        // 返回值
+        ExampleResult exampleResult = new ExampleResult();
+        exampleResult.setDeleteExample(false);
+
+        // 创建流程实例
+        ExampleInfo oleExampleInfo = exampleInfoService.getOne(Wrappers.<ExampleInfo>lambdaQuery()
+                .eq(ExampleInfo::getFlowLinkNo, jumpVo.getFlowLinkNo())
+                .eq(ExampleInfo::getComplete, StatusConstant.NO));
+
+        ExampleInfo exampleInfo = ObjectUtil.clone(oleExampleInfo);
+        Assert.notEmpty(exampleInfo, FlowExplainConstant.EXAMPLE_INFO_NULL);
+
+        String cacheDataStr = jumpVo.getCacheDataStr();
+        if (ObjectUtil.isNotEmpty(cacheDataStr)) {
+            exampleInfo.setCacheData(cacheDataStr);
+        }
+
+        // 明细
+        ExampleDetails exampleDetails = createExampleDetails(exampleInfo, jumpVo.getNameType());
+        exampleDetails.setProcessNodeId(exampleInfo.getProcessNodeId());
+        exampleDetails.setProcessNodeButtonId(jumpVo.getButtonId());
+        exampleDetails.setRemarks(jumpVo.getRemarks());
+        exampleDetails.setHandleUserId(AuthUtil.getUserId());
+
+        // 流程结束
+        if (FlowConstant.END_CODE.equals(jumpVo.getJumpNodeCode())) {
+
+            // 赋值流程结束
+            exampleInfoEnd(exampleInfo);
+            exampleInfo.setHandleResult(HandleResultEnum.ADOPT.getType());
+            exampleInfoService.updateById(exampleInfo);
+
+            // 结束明细
+            ExampleDetails endExampleDetails = createExampleDetails(exampleInfo, ButtonNameEnum.END.getType());
+
+            exampleResult.setOldExampleInfo(oleExampleInfo);
+            exampleResult.setCacheDataStr(exampleInfo.getCacheData());
+            exampleResult.setExampleDetailsIdList(Arrays.asList(exampleDetails.getId(), endExampleDetails.getId()));
+            exampleResult.setHandleType(ButtonNameEnum.END.getType());
+
+            return R.data(exampleResult);
+        }
+
+        // 如果是自定义节点跳转
+        if (jumpVo.isSpecifyJump()) {
+            List<ProcessNodeButton> list = processNodeButtonService.list(Wrappers.<ProcessNodeButton>lambdaQuery()
+                    .eq(ProcessNodeButton::getProcessTenantId, exampleInfo.getProcessTenantId())
+                    .eq(ProcessNodeButton::getProcessNodeCode, jumpVo.getJumpNodeCode()));
+
+            if (list.size() == 0) {
+                throw new ServiceException(FlowExplainConstant.NOT_CODE);
+            }
+
+            if (list.size() > 1) {
+                throw new ServiceException(FlowExplainConstant.MULTIPLE_CODE);
+            }
+
+            ProcessNodeButton processNodeButton = list.get(0);
+            jumpVo.setJumpNodeId(processNodeButton.getJumpNodeId());
+            jumpVo.setJumpNodeCode(processNodeButton.getJumpNodeCode());
+            jumpVo.setNameType(processNodeButton.getNameType());
+        }
+
+        // 通过结束
+        if (ButtonNameEnum.END.getType().equals(jumpVo.getNameType())) {
+            exampleInfoEnd(exampleInfo);
+            exampleInfo.setHandleResult(HandleResultEnum.ADOPT.getType());
+            ExampleDetails endExampleDetails = createExampleDetails(exampleInfo, ButtonNameEnum.END.getType());
+            exampleResult.setExampleDetailsIdList(Arrays.asList(exampleDetails.getId(), endExampleDetails.getId()));
+        }
+        // 驳回结束
+        else if (ButtonNameEnum.REJECT.getType().equals(jumpVo.getNameType())) {
+            exampleInfoEnd(exampleInfo);
+            exampleInfo.setHandleResult(HandleResultEnum.FAIL.getType());
+            ExampleDetails endExampleDetails = createExampleDetails(exampleInfo, ButtonNameEnum.END.getType());
+            exampleResult.setExampleDetailsIdList(Arrays.asList(exampleDetails.getId(), endExampleDetails.getId()));
+        }
+        // 流程流转
+        else {
+            exampleInfo.setProcessNodeId(jumpVo.getJumpNodeId());
+            exampleInfo.setProcessNodeCode(jumpVo.getJumpNodeCode());
+            exampleInfo.setHandleResult(HandleResultEnum.START.getType());
+            exampleResult.setExampleDetailsIdList(Collections.singletonList(exampleDetails.getId()));
+        }
+
+        exampleInfoService.updateById(exampleInfo);
+        exampleResult.setOldExampleInfo(oleExampleInfo);
+        exampleResult.setCacheDataStr(exampleInfo.getCacheData());
+        exampleResult.setHandleType(jumpVo.getNameType());
+
+        return R.data(exampleResult);
+    }
+
+    @GetMapping(ROLL_BACK)
+    @Override
+    public void rollBack(ExampleResult result) {
+        ExampleInfo oldExampleInfo = result.getOldExampleInfo();
+
+        if (result.isDeleteExample()) {
+            exampleInfoService.removeById(oldExampleInfo.getId());
+        } else {
+            exampleInfoService.updateById(oldExampleInfo);
+        }
+
+        List<Long> exampleDetailsIdList = result.getExampleDetailsIdList();
+        exampleDetailsService.removeByIds(exampleDetailsIdList);
+    }
+
+    /**
+     * 获取流程结束明细
+     */
+    private ExampleDetails createExampleDetails(ExampleInfo exampleInfo, Integer nameType) {
+        return createExampleDetails(
+                exampleInfo.getId(), exampleInfo.getProcessInfoId(), exampleInfo.getProcessTenantId(), nameType);
+    }
+
+
+    private ExampleDetails createExampleDetails(Long exampleInfoId, Long processInfoId, Long processTenantId, Integer nameType) {
+        ExampleDetails endExampleDetails = new ExampleDetails();
+        endExampleDetails.setExampleInfoId(exampleInfoId);
+        endExampleDetails.setProcessInfoId(processInfoId);
+        endExampleDetails.setProcessTenantId(processTenantId);
+        endExampleDetails.setNameType(nameType);
+        return endExampleDetails;
+    }
 
-        return null;
+    /**
+     * 赋值实例结束参数
+     */
+    private void exampleInfoEnd(ExampleInfo exampleInfo) {
+        exampleInfo.setComplete(StatusConstant.YES);
+        exampleInfo.setProcessNodeId(FlowConstant.OVER_PROCESS_FLAG);
+        exampleInfo.setProcessNodeCode(FlowConstant.END_CODE);
     }
 
 }

+ 3 - 2
hx-common/service-flow/src/main/java/com/fjhx/service/example/impl/ExampleInfoServiceImpl.java

@@ -51,7 +51,7 @@ public class ExampleInfoServiceImpl extends ServiceImpl<ExampleInfoMapper, Examp
                                 "remarks", // 审批意见
                                 "name_type type", // 处理类型
                                 "process_node_id nodeId", // 节点id
-                                "create_"
+                                "create_time createTime"
                         )
                         .lambda()
                         .eq(ExampleDetails::getExampleInfoId, exampleInfo.getId())
@@ -93,6 +93,7 @@ public class ExampleInfoServiceImpl extends ServiceImpl<ExampleInfoMapper, Examp
 
             }
 
+            // 下一个节点进行中
             Map<String, Object> map = result.get(result.size() - 1);
             List<ProcessNode> processNodes = parentProcessNodeMap.get((Long) map.get("nodeId"));
             if (processNodes != null && processNodes.size() == 1) {
@@ -112,7 +113,7 @@ public class ExampleInfoServiceImpl extends ServiceImpl<ExampleInfoMapper, Examp
             }
         }
 
-        // 寻找之后未处理的节点
+        // 寻找之后未处理的节点(未开始)
         while (nextNode != null) {
             HashMap<String, Object> map = new HashMap<>();
             map.put("type", ButtonNameEnum.NOT_STARTED.getType());

+ 64 - 33
hx-common/service-flow/src/main/java/com/fjhx/service/process/impl/ProcessNodeButtonServiceImpl.java

@@ -38,6 +38,22 @@ public class ProcessNodeButtonServiceImpl extends ServiceImpl<ProcessNodeButtonM
 
         // 赋值节点id
         for (ProcessNode processNode : processNodeList) {
+            Integer type = processNode.getType();
+
+            // 获取节点类型枚举值
+            ProcessNodeTypeEnum processNodeTypeEnum = ProcessNodeTypeEnum.get(type);
+
+            Assert.notEmpty(processNodeTypeEnum, FlowExplainConstant.NODE_UNKNOWN);
+
+            // 开始节点编码
+            if (processNodeTypeEnum.equals(ProcessNodeTypeEnum.START)) {
+                processNode.setCode(FlowConstant.START_CODE);
+            }
+
+            // 结束节点编码
+            else if (processNodeTypeEnum.equals(ProcessNodeTypeEnum.END)) {
+                processNode.setCode(FlowConstant.END_CODE);
+            }
 
             processNode.setProcessTenantId(nodeDetailsVo.getProcessTenantId());
 
@@ -56,11 +72,11 @@ public class ProcessNodeButtonServiceImpl extends ServiceImpl<ProcessNodeButtonM
 
 
         // 按父级节点id分组
-        Map<Long, List<ProcessNode>> ProcessNodeGroupByParentId = processNodeList.stream()
+        Map<Long, List<ProcessNode>> processNodeGroupByParentId = processNodeList.stream()
                 .collect(Collectors.groupingBy(ProcessNode::getParentId));
 
         // 按节点id分组
-        Map<Long, List<ProcessNode>> ProcessNodeGroupById = processNodeList.stream()
+        Map<Long, List<ProcessNode>> processNodeGroupById = processNodeList.stream()
                 .collect(Collectors.groupingBy(ProcessNode::getId));
 
         // 根据节点类型生成功能按钮
@@ -68,29 +84,25 @@ public class ProcessNodeButtonServiceImpl extends ServiceImpl<ProcessNodeButtonM
 
         for (ProcessNode processNode : processNodeList) {
 
-            Integer type = processNode.getType();
-
             // 获取节点类型枚举值
-            ProcessNodeTypeEnum processNodeTypeEnum = ProcessNodeTypeEnum.get(type);
-
-            Assert.notEmpty(processNodeTypeEnum, FlowExplainConstant.NODE_UNKNOWN);
+            ProcessNodeTypeEnum processNodeTypeEnum = ProcessNodeTypeEnum.get(processNode.getType());
 
             switch (processNodeTypeEnum) {
 
                 case START: // 开始
-                    startHandle(processNodeButtonList, ProcessNodeGroupByParentId, processNode);
+                    startHandle(processNodeButtonList, processNodeGroupById, processNodeGroupByParentId, processNode);
                     break;
 
                 case EXAMINED: // 审核
-                    examinedHandle(processNodeButtonList, ProcessNodeGroupById, ProcessNodeGroupByParentId, processNode);
+                    examinedHandle(processNodeButtonList, processNodeGroupById, processNodeGroupByParentId, processNode);
                     break;
 
                 case APPROVAL: // 审批
-                    approvalHandle(processNodeButtonList, ProcessNodeGroupByParentId, processNode);
+                    approvalHandle(processNodeButtonList, processNodeGroupByParentId, processNode);
                     break;
 
                 case HANDLE: // 办理
-                    handle(processNodeButtonList, ProcessNodeGroupByParentId, processNode);
+                    handle(processNodeButtonList, processNodeGroupByParentId, processNode);
                     break;
 
                 case BRANCH: // 分支
@@ -98,6 +110,7 @@ public class ProcessNodeButtonServiceImpl extends ServiceImpl<ProcessNodeButtonM
                     break;
 
                 case END: // 结束
+                    endHandle(processNodeGroupByParentId, processNode);
                     break;
 
             }
@@ -111,9 +124,17 @@ public class ProcessNodeButtonServiceImpl extends ServiceImpl<ProcessNodeButtonM
      * 开始节点处理
      */
     private void startHandle(List<ProcessNodeButton> processNodeButtonList,
-                             Map<Long, List<ProcessNode>> ProcessNodeGroupByParentId, ProcessNode processNode) {
+                             Map<Long, List<ProcessNode>> processNodeGroupById,
+                             Map<Long, List<ProcessNode>> processNodeGroupByParentId,
+                             ProcessNode processNode) {
+
+        List<ProcessNode> previousProcessNodeList = processNodeGroupById.get(processNode.getParentId());
+        if (previousProcessNodeList != null) {
+            throw new ServiceException(String.format(FlowExplainConstant.PREVIOUS_ERROR, processNode.getName()));
+        }
+
         // 下一步
-        ProcessNodeButton next = next(ProcessNodeGroupByParentId, processNode, ButtonNameEnum.START);
+        ProcessNodeButton next = next(processNodeGroupByParentId, processNode, ButtonNameEnum.START);
         processNodeButtonList.add(next);
     }
 
@@ -121,14 +142,14 @@ public class ProcessNodeButtonServiceImpl extends ServiceImpl<ProcessNodeButtonM
      * 审核处理
      */
     private void examinedHandle(List<ProcessNodeButton> processNodeButtonList,
-                                Map<Long, List<ProcessNode>> ProcessNodeGroupById,
-                                Map<Long, List<ProcessNode>> ProcessNodeGroupByParentId,
+                                Map<Long, List<ProcessNode>> processNodeGroupById,
+                                Map<Long, List<ProcessNode>> processNodeGroupByParentId,
                                 ProcessNode processNode) {
         // 通过
-        ProcessNodeButton next = next(ProcessNodeGroupByParentId, processNode, ButtonNameEnum.ADOPT);
+        ProcessNodeButton next = next(processNodeGroupByParentId, processNode, ButtonNameEnum.ADOPT);
         processNodeButtonList.add(next);
         // 驳回
-        ProcessNodeButton previous = previous(ProcessNodeGroupById, processNode, ButtonNameEnum.FAIL);
+        ProcessNodeButton previous = previous(processNodeGroupById, processNode, ButtonNameEnum.FAIL);
         processNodeButtonList.add(previous);
     }
 
@@ -136,9 +157,9 @@ public class ProcessNodeButtonServiceImpl extends ServiceImpl<ProcessNodeButtonM
      * 审批处理
      */
     private void approvalHandle(List<ProcessNodeButton> processNodeButtonList,
-                                Map<Long, List<ProcessNode>> ProcessNodeGroupByParentId, ProcessNode processNode) {
+                                Map<Long, List<ProcessNode>> processNodeGroupByParentId, ProcessNode processNode) {
         // 同意
-        ProcessNodeButton next = next(ProcessNodeGroupByParentId, processNode, ButtonNameEnum.AGREE);
+        ProcessNodeButton next = next(processNodeGroupByParentId, processNode, ButtonNameEnum.AGREE);
         processNodeButtonList.add(next);
         // 驳回
         ProcessNodeButton over = over(processNode, ButtonNameEnum.REJECT);
@@ -149,9 +170,9 @@ public class ProcessNodeButtonServiceImpl extends ServiceImpl<ProcessNodeButtonM
      * 办理处理
      */
     private void handle(List<ProcessNodeButton> processNodeButtonList,
-                        Map<Long, List<ProcessNode>> ProcessNodeGroupByParentId, ProcessNode processNode) {
+                        Map<Long, List<ProcessNode>> processNodeGroupByParentId, ProcessNode processNode) {
         // 完成
-        ProcessNodeButton next = next(ProcessNodeGroupByParentId, processNode, ButtonNameEnum.COMPLETE);
+        ProcessNodeButton next = next(processNodeGroupByParentId, processNode, ButtonNameEnum.COMPLETE);
         processNodeButtonList.add(next);
     }
 
@@ -164,15 +185,26 @@ public class ProcessNodeButtonServiceImpl extends ServiceImpl<ProcessNodeButtonM
     }
 
     /**
+     * 结束
+     */
+    private void endHandle(Map<Long, List<ProcessNode>> processNodeGroupByParentId, ProcessNode processNode) {
+        List<ProcessNode> nextProcessNodeList = processNodeGroupByParentId.get(processNode.getId());
+        if (nextProcessNodeList != null) {
+            throw new ServiceException(String.format(FlowExplainConstant.JUMP_EMPTY, processNode.getName()));
+        }
+    }
+
+
+    /**
      * 跳转上一节点
      */
-    private ProcessNodeButton previous(Map<Long, List<ProcessNode>> ProcessNodeGroupById,
+    private ProcessNodeButton previous(Map<Long, List<ProcessNode>> processNodeGroupById,
                                        ProcessNode processNode, ButtonNameEnum buttonNameEnum) {
 
         ProcessNodeButton processNodeButton = createProcessNodeButton(processNode, buttonNameEnum);
 
         // 赋值跳转到上一节点
-        List<ProcessNode> previousProcessNodeList = ProcessNodeGroupById.get(processNode.getParentId());
+        List<ProcessNode> previousProcessNodeList = processNodeGroupById.get(processNode.getParentId());
         if (previousProcessNodeList == null || previousProcessNodeList.size() != 1) {
             throw new ServiceException(String.format(FlowExplainConstant.PREVIOUS_ERROR, processNode.getName()));
         }
@@ -181,39 +213,37 @@ public class ProcessNodeButtonServiceImpl extends ServiceImpl<ProcessNodeButtonM
         ProcessNode node = previousProcessNodeList.get(0);
         if (node.getType().equals(ProcessNodeTypeEnum.BRANCH.getType())) {
 
-            previousProcessNodeList = ProcessNodeGroupById.get(node.getParentId());
+            previousProcessNodeList = processNodeGroupById.get(node.getParentId());
             if (previousProcessNodeList == null || previousProcessNodeList.size() != 1) {
                 throw new ServiceException(String.format(FlowExplainConstant.PREVIOUS_ERROR, processNode.getName()));
             }
 
-            processNodeButton.setJumpNodeId(node.getParentId());
+            processNodeButton.setJumpNodeId(previousProcessNodeList.get(0).getId());
+            processNodeButton.setJumpNodeCode(previousProcessNodeList.get(0).getCode());
         } else {
             processNodeButton.setJumpNodeId(node.getId());
+            processNodeButton.setJumpNodeCode(node.getCode());
         }
 
-
         return processNodeButton;
     }
 
     /**
      * 跳转下一节点
      */
-    private ProcessNodeButton next(Map<Long, List<ProcessNode>> ProcessNodeGroupByParentId,
+    private ProcessNodeButton next(Map<Long, List<ProcessNode>> processNodeGroupByParentId,
                                    ProcessNode processNode, ButtonNameEnum buttonNameEnum) {
         ProcessNodeButton processNodeButton = createProcessNodeButton(processNode, buttonNameEnum);
 
         // 赋值跳转到下一节点
-        List<ProcessNode> nextProcessNodeList = ProcessNodeGroupByParentId.get(processNode.getId());
+        List<ProcessNode> nextProcessNodeList = processNodeGroupByParentId.get(processNode.getId());
         if (nextProcessNodeList == null || nextProcessNodeList.size() != 1) {
             throw new ServiceException(String.format(FlowExplainConstant.JUMP_EMPTY, processNode.getName()));
         }
 
         ProcessNode itemProcessNode = nextProcessNodeList.get(0);
-        if (itemProcessNode.getType().equals(ProcessNodeTypeEnum.END.getType())) {
-            processNodeButton.setJumpNodeId(FlowConstant.OVER_PROCESS_FLAG);
-        } else {
-            processNodeButton.setJumpNodeId(itemProcessNode.getId());
-        }
+        processNodeButton.setJumpNodeId(itemProcessNode.getId());
+        processNodeButton.setJumpNodeCode(itemProcessNode.getCode());
         return processNodeButton;
     }
 
@@ -223,6 +253,7 @@ public class ProcessNodeButtonServiceImpl extends ServiceImpl<ProcessNodeButtonM
     private ProcessNodeButton over(ProcessNode processNode, ButtonNameEnum buttonNameEnum) {
         ProcessNodeButton processNodeButton = createProcessNodeButton(processNode, buttonNameEnum);
         processNodeButton.setJumpNodeId(FlowConstant.OVER_PROCESS_FLAG);
+        processNodeButton.setJumpNodeCode(FlowConstant.END_CODE);
         return processNodeButton;
     }
 

+ 5 - 0
hx-service-api/service-flow-api/src/main/java/com/fjhx/constants/FlowExplainConstant.java

@@ -55,4 +55,9 @@ public interface FlowExplainConstant {
 
     String EXAMPLE_INFO_NULL = "流程未发起或已结束";
 
+    String NOT_CODE = "没有找到节点编码";
+
+    String MULTIPLE_CODE = "匹配到多个节点编码";
+
+
 }

+ 5 - 0
hx-service-api/service-flow-api/src/main/java/com/fjhx/entity/example/ExampleInfo.java

@@ -45,6 +45,11 @@ public class ExampleInfo extends BaseEntity {
     private String processNodeCode;
 
     /**
+     * 处理结果
+     */
+    private Integer handleResult;
+
+    /**
      * 是否完成
      */
     private Integer complete;

+ 5 - 0
hx-service-api/service-flow-api/src/main/java/com/fjhx/entity/process/ProcessNodeButton.java

@@ -50,4 +50,9 @@ public class ProcessNodeButton implements Serializable {
      */
     private Long jumpNodeId;
 
+    /**
+     * 跳转节点code
+     */
+    private String jumpNodeCode;
+
 }

+ 43 - 0
hx-service-api/service-flow-api/src/main/java/com/fjhx/enums/HandleResultEnum.java

@@ -0,0 +1,43 @@
+package com.fjhx.enums;
+
+import lombok.Getter;
+
+import java.util.HashMap;
+
+@Getter
+public enum HandleResultEnum {
+    NOT_START(1, "未开始"),
+    START(2, "已开始"),
+    ADOPT(3, "通过"),
+    FAIL(4, "不通过");
+
+    private final Integer type;
+    private final String name;
+
+    private static final HashMap<Integer, ButtonNameEnum> map = new HashMap<>();
+
+    HandleResultEnum(Integer type, String name) {
+        this.type = type;
+        this.name = name;
+    }
+
+    static {
+        for (ButtonNameEnum value : ButtonNameEnum.values()) {
+            map.put(value.getType(), value);
+        }
+    }
+
+    /**
+     * 根据type获取枚举
+     */
+    public static ButtonNameEnum get(Integer type) {
+        return map.get(type);
+    }
+
+    /**
+     * 根据type值获取枚举
+     */
+    public static String getName(Integer type) {
+        return map.get(type).getName();
+    }
+}

+ 29 - 5
hx-service-api/service-flow-api/src/main/java/com/fjhx/feign/IFlowClient.java

@@ -3,10 +3,7 @@ package com.fjhx.feign;
 import com.fjhx.constants.ClientConstant;
 import com.fjhx.entity.example.ExampleInfo;
 import com.fjhx.entity.process.ProcessNodeButton;
-import com.fjhx.params.ExampleInfoEx;
-import com.fjhx.params.ExampleResult;
-import com.fjhx.params.FlowInfoVo;
-import com.fjhx.params.GetNodeButtonVo;
+import com.fjhx.params.*;
 import org.springblade.core.tool.api.R;
 import org.springframework.cloud.openfeign.FeignClient;
 import org.springframework.web.bind.annotation.GetMapping;
@@ -25,6 +22,9 @@ public interface IFlowClient {
     String EXAMPLE_INFO_SAVE = ClientConstant.API_PREFIX + "/exampleInfoSave";
     String GET_EXAMPLE_INFO = ClientConstant.API_PREFIX + "/getExampleInfo";
     String CREATE = ClientConstant.API_PREFIX + "/create";
+    String GET_NODE_BUTTON_BY_ID = ClientConstant.API_PREFIX + "/getNodeButtonById";
+    String JUMP = ClientConstant.API_PREFIX + "/jump";
+    String ROLL_BACK = ClientConstant.API_PREFIX + "/rollBack";
 
     /**
      * 通过流程编码获取流程信息
@@ -58,7 +58,6 @@ public interface IFlowClient {
      * @param nodeCode   跳转节点编码
      * @param remarks    发起原因/处理意见
      * @param cacheData  缓存数据
-     * @return
      */
     @GetMapping(CREATE)
     R<ExampleResult> create(@RequestParam("flowLinkNo") Long flowLinkNo,
@@ -67,4 +66,29 @@ public interface IFlowClient {
                             @RequestParam("remarks") String remarks,
                             @RequestParam("cacheData") String cacheData);
 
+    /**
+     * 获取按钮
+     *
+     * @param buttonId 按钮id
+     * @return 按钮对象
+     */
+    @GetMapping(GET_NODE_BUTTON_BY_ID)
+    R<ProcessNodeButton> getNodeButtonById(@RequestParam("buttonId") Long buttonId);
+
+    /**
+     * 流程跳转
+     *
+     * @param jumpVo 参数
+     */
+    @GetMapping(JUMP)
+    R<ExampleResult> jump(JumpVo jumpVo);
+
+    /**
+     * 异常回滚
+     *
+     * @param result
+     */
+    @GetMapping(ROLL_BACK)
+    void rollBack(ExampleResult result);
+
 }

+ 6 - 1
hx-service-api/service-flow-api/src/main/java/com/fjhx/params/ExampleResult.java

@@ -11,7 +11,7 @@ public class ExampleResult {
     /**
      * 流程实例
      */
-    private ExampleInfo exampleInfo;
+    private ExampleInfo oldExampleInfo;
 
     /**
      * 流程实例明细id
@@ -28,4 +28,9 @@ public class ExampleResult {
      */
     private String cacheDataStr;
 
+    /**
+     * 回滚是否删除流程实例
+     */
+    private boolean deleteExample;
+
 }

+ 48 - 0
hx-service-api/service-flow-api/src/main/java/com/fjhx/params/JumpVo.java

@@ -0,0 +1,48 @@
+package com.fjhx.params;
+
+import lombok.Data;
+
+@Data
+public class JumpVo {
+
+    /**
+     * 流程关联编号
+     */
+    private Long flowLinkNo;
+
+    /**
+     * 按钮id
+     */
+    private Long buttonId;
+
+    /**
+     * 审批意见
+     */
+    private String remarks;
+
+    /**
+     * 缓存字符串
+     */
+    private String cacheDataStr;
+
+    /**
+     * 是否根据编码指定跳转
+     */
+    private boolean specifyJump;
+
+    /**
+     * 跳转节点id
+     */
+    private Long jumpNodeId;
+
+    /**
+     * 跳转节点code
+     */
+    private String jumpNodeCode;
+
+    /**
+     * 按钮类型
+     */
+    private Integer nameType;
+
+}

+ 2 - 2
hx-service-api/service-flow-api/src/main/java/com/fjhx/utils/ExampleAbstract.java

@@ -34,12 +34,12 @@ public abstract class ExampleAbstract {
     public abstract void end();
 
     /**
-     * 审批不通过方法(直接结束流程)
+     * 审批驳回方法(直接结束流程)
      * 需要时重写即可
      *
      * @param code 节点编码
      */
-    public void fail(String code) {
+    public void reject(String code) {
 
     }
 

+ 1 - 1
hx-service-api/service-flow-api/src/main/java/com/fjhx/utils/FlowConstructor.java

@@ -172,7 +172,7 @@ public class FlowConstructor {
         else if (ButtonNameEnum.REJECT.getType().equals(processNodeButton.getNameType())) {
             exampleInfo.setComplete(StatusConstant.YES);
             exampleInfo.setProcessNodeCode(FlowConstant.END_CODE);
-            exampleAbstract.fail(processNodeButton.getProcessNodeCode());
+            exampleAbstract.reject(processNodeButton.getProcessNodeCode());
         }
         // 正常流转到下一节点
         else {

+ 103 - 133
hx-service-api/service-flow-api/src/main/java/com/fjhx/utils/FlowConstructorBack.java

@@ -1,20 +1,15 @@
 package com.fjhx.utils;
 
-import cn.hutool.core.bean.BeanUtil;
 import cn.hutool.core.util.ObjectUtil;
 import cn.hutool.extra.spring.SpringUtil;
 import com.alibaba.fastjson.JSONObject;
 import com.fjhx.constants.FlowConstant;
 import com.fjhx.constants.FlowExplainConstant;
-import com.fjhx.constants.StatusConstant;
-import com.fjhx.entity.example.ExampleDetails;
-import com.fjhx.entity.example.ExampleInfo;
 import com.fjhx.entity.process.ProcessNodeButton;
 import com.fjhx.enums.ButtonNameEnum;
 import com.fjhx.feign.IFlowClient;
-import com.fjhx.params.ExampleInfoEx;
 import com.fjhx.params.ExampleResult;
-import com.fjhx.params.GetNodeButtonVo;
+import com.fjhx.params.JumpVo;
 import org.springblade.core.tool.api.R;
 
 public class FlowConstructorBack {
@@ -23,6 +18,13 @@ public class FlowConstructorBack {
 
     private final ExampleAbstract exampleAbstract;
 
+    /**
+     * 初始化
+     */
+    public static FlowConstructorBack init(ExampleAbstract exampleAbstract) {
+        return new FlowConstructorBack(exampleAbstract);
+    }
+
     private FlowConstructorBack(ExampleAbstract exampleAbstract) {
         this.exampleAbstract = exampleAbstract;
     }
@@ -33,93 +35,34 @@ public class FlowConstructorBack {
      * @param flowLinkNo 流程关联编号
      * @return 流程实例对象
      */
-    public ExampleInfo create(Long flowLinkNo, String remarks, Object cacheData) {
+    public ExampleResult create(Long flowLinkNo, String remarks, Object cacheData) {
 
         // 获取流程编码
-        String code = exampleAbstract.getCode();
-        Assert.notEmpty(code, FlowExplainConstant.CODE_EMPTY);
+        String code = getCode();
 
-        String cacheDataStr = "";
-        if (ObjectUtil.isNotEmpty(cacheData)) {
-            cacheDataStr = JSONObject.toJSONString(cacheData);
-        }
+        // 缓存对象转字符串
+        String cacheDataStr = getCacheDataStr(cacheData);
 
         // 查询跳转节点
         String nodeCode = exampleAbstract.circulation(FlowConstant.START_CODE);
 
+        // 执行流程
         R<ExampleResult> exampleResultR = flowClient.create(flowLinkNo, code, nodeCode, remarks, cacheDataStr);
+        ExampleResult result = Assert.result(exampleResultR);
+
+        exampleAbstract.setCacheData(cacheData);
+
+        // 如果流程结束,执行结束方法
+        if (ButtonNameEnum.END.getType().equals(result.getHandleType())) {
+            try {
+                exampleAbstract.end();
+            } catch (Exception e) {
+                rollBack(result);
+                throw e;
+            }
+        }
 
-
-//        // 创建流程实例
-//        ExampleInfoEx exampleInfo = new ExampleInfoEx();
-//        exampleInfo.setProcessInfoId(flowInfoVo.getId());
-//        exampleInfo.setFlowLinkNo(flowLinkNo);
-//        if (ObjectUtil.isNotEmpty(exampleAbstract.cacheData)) {
-//            exampleInfo.setCacheData(JSONObject.toJSONString(exampleAbstract.cacheData));
-//        }
-//
-//        ExampleDetails startExampleDetails = new ExampleDetails();
-//        startExampleDetails.setRemarks(remarks);
-//
-//        // 如果租户流程为空,直接完成流程
-//        ProcessTenant processTenant = flowInfoVo.processTenantEntity();
-//        if (ObjectUtil.isEmpty(processTenant)) {
-//            exampleInfo.setProcessNodeId(FlowConstant.OVER_PROCESS_FLAG);
-//            exampleInfo.setComplete(StatusConstant.YES);
-//            exampleInfo.setProcessNodeCode(FlowConstant.END_CODE);
-//
-//            startExampleDetails.setNameType(ButtonNameEnum.START.getType());
-//            // 执行流程结束方法
-//            exampleAbstract.end();
-//        }
-//        // 租户流程不为空,走租户流程
-//        else {
-//            Long processTenantId = processTenant.getId();
-//
-//            // 赋值租户流程id
-//            exampleInfo.setProcessTenantId(processTenantId);
-//
-//            // 调用方法查看是否有指定跳转节点,没有则正常流转
-////            String circulation = exampleAbstract.circulation(FlowConstant.START_CODE);
-//
-//            GetNodeButtonVo getNodeButtonVo = new GetNodeButtonVo();
-//            getNodeButtonVo.setProcessTenantId(processTenantId);
-//            getNodeButtonVo.setNodeCode(ObjectUtil.isEmpty(circulation) ? FlowConstant.START_CODE : circulation);
-//
-//            R<ProcessNodeButton> nodeButtonResult = flowClient.getNodeButton(getNodeButtonVo);
-//            Assert.eqTrue(nodeButtonResult.isSuccess(), nodeButtonResult.getMsg());
-//
-//            ProcessNodeButton processNodeButton = nodeButtonResult.getData();
-//            startExampleDetails.setProcessNodeId(processNodeButton.getProcessNodeId());
-//            startExampleDetails.setProcessNodeButtonId(processNodeButton.getId());
-//            startExampleDetails.setNameType(processNodeButton.getNameType());
-//
-//            // 流转节点
-//            Long jumpNodeId = processNodeButton.getJumpNodeId();
-//
-//            // 流程结束
-//            if (jumpNodeId.equals(FlowConstant.OVER_PROCESS_FLAG)) {
-//                exampleInfo.setComplete(StatusConstant.YES);
-//                exampleInfo.setProcessNodeCode(FlowConstant.END_CODE);
-//                exampleAbstract.end();
-//            }
-//            // 正常流转到下一节点
-//            else {
-//                exampleInfo.setComplete(StatusConstant.NO);
-//            }
-//
-//            // 赋值跳转节点id
-//            exampleInfo.setProcessNodeId(jumpNodeId);
-//            exampleInfo.setProcessNodeCode(processNodeButton.getProcessNodeCode());
-//        }
-//        exampleInfo.setExampleDetails(startExampleDetails);
-//
-//        // 保存流程实例
-//        R<ExampleInfo> exampleInfoSaveResult = flowClient.exampleInfoSave(exampleInfo);
-//        Assert.eqTrue(exampleInfoSaveResult.isSuccess(), exampleInfoSaveResult.getMsg());
-
-//        return exampleInfoSaveResult.getData();
-        return null;
+        return result;
     }
 
     /**
@@ -128,69 +71,96 @@ public class FlowConstructorBack {
      * @param flowLinkNo 流程关联编号
      * @param buttonId   按钮id
      * @param remarks    审批意见
+     * @param cacheData  缓存对象
      */
-    public void jump(Long flowLinkNo, Long buttonId, String remarks) {
-
-        R<ExampleInfo> exampleInfoResult = flowClient.getExampleInfo(flowLinkNo);
-        Assert.eqTrue(exampleInfoResult.isSuccess(), exampleInfoResult.getMsg());
+    public ExampleResult jump(Long flowLinkNo, Long buttonId, String remarks, Object cacheData) {
 
-        ExampleInfo exampleInfo = exampleInfoResult.getData();
+        // 缓存对象转字符串
+        String cacheDataStr = getCacheDataStr(cacheData);
 
-        // 获取流程缓存
-        exampleAbstract.cacheData = exampleInfo.getCacheData();
+        // 获取按钮
+        ProcessNodeButton processNodeButton = Assert.result(flowClient.getNodeButtonById(buttonId));
 
-        // 赋值新缓存
-        if (ObjectUtil.isNotEmpty(exampleAbstract.cacheData)) {
-            exampleInfo.setCacheData(JSONObject.toJSONString(exampleAbstract.cacheData));
+        // 查询跳转节点
+        String processNodeCode = processNodeButton.getProcessNodeCode();
+        String nodeCode = exampleAbstract.circulation(processNodeCode);
+
+        JumpVo jumpVo = new JumpVo();
+        jumpVo.setFlowLinkNo(flowLinkNo);
+        jumpVo.setButtonId(buttonId);
+        jumpVo.setRemarks(remarks);
+        jumpVo.setCacheDataStr(cacheDataStr);
+        if (ObjectUtil.isNotEmpty(nodeCode)) {
+            jumpVo.setSpecifyJump(true);
+            jumpVo.setJumpNodeCode(nodeCode);
+        } else {
+            jumpVo.setSpecifyJump(false);
+            jumpVo.setJumpNodeId(processNodeButton.getJumpNodeId());
+            jumpVo.setJumpNodeCode(processNodeButton.getJumpNodeCode());
+            jumpVo.setNameType(processNodeButton.getNameType());
         }
 
-        // 调用方法查看是否有指定跳转节点,没有则正常流转
-        GetNodeButtonVo getNodeButtonVo = new GetNodeButtonVo();
-        getNodeButtonVo.setProcessTenantId(exampleInfo.getProcessTenantId());
-        getNodeButtonVo.setNodeCode(exampleAbstract.circulation(exampleInfo.getProcessNodeCode()));
-        getNodeButtonVo.setButtonId(buttonId);
-
-        R<ProcessNodeButton> nodeButtonResult = flowClient.getNodeButton(getNodeButtonVo);
-        Assert.eqTrue(nodeButtonResult.isSuccess(), nodeButtonResult.getMsg());
+        R<ExampleResult> exampleResultR = flowClient.jump(jumpVo);
+        ExampleResult result = Assert.result(exampleResultR);
 
-        ProcessNodeButton processNodeButton = nodeButtonResult.getData();
+        exampleAbstract.setCacheData(cacheData);
 
-        // 赋值跳转节点id
-        exampleInfo.setProcessNodeId(processNodeButton.getJumpNodeId());
-        exampleInfo.setProcessNodeCode(processNodeButton.getProcessNodeCode());
-
-        // 流程正常结束
-        if (processNodeButton.getJumpNodeId().equals(FlowConstant.OVER_PROCESS_FLAG)) {
-            exampleInfo.setComplete(StatusConstant.YES);
-            exampleInfo.setProcessNodeCode(FlowConstant.END_CODE);
-            exampleAbstract.end();
-        }
-        // 驳回结束
-        else if (ButtonNameEnum.REJECT.getType().equals(processNodeButton.getNameType())) {
-            exampleInfo.setComplete(StatusConstant.YES);
-            exampleInfo.setProcessNodeCode(FlowConstant.END_CODE);
-            exampleAbstract.fail(processNodeButton.getProcessNodeCode());
+        // 如果流程结束,执行结束方法
+        if (ButtonNameEnum.END.getType().equals(result.getHandleType())) {
+            try {
+                exampleAbstract.end();
+            } catch (Exception e) {
+                rollBack(result);
+                throw e;
+            }
         }
-        // 正常流转到下一节点
-        else {
-            exampleInfo.setComplete(StatusConstant.NO);
+
+        // 如果流程结束,执行结束方法
+        if (ButtonNameEnum.REJECT.getType().equals(result.getHandleType())) {
+            try {
+                exampleAbstract.reject(result.getOldExampleInfo().getProcessNodeCode());
+            } catch (Exception e) {
+                rollBack(result);
+                throw e;
+            }
         }
 
-        // 流程明细
-        ExampleDetails startExampleDetails = new ExampleDetails();
-        startExampleDetails.setRemarks(remarks);
-        startExampleDetails.setProcessNodeId(processNodeButton.getProcessNodeId());
-        startExampleDetails.setProcessNodeButtonId(processNodeButton.getId());
-        startExampleDetails.setNameType(processNodeButton.getNameType());
+        return result;
+    }
 
-        // 创建vo
-        ExampleInfoEx exampleInfoEx = BeanUtil.toBean(exampleInfo, ExampleInfoEx.class);
-        exampleInfoEx.setExampleDetails(startExampleDetails);
+    /**
+     * 业务异常回滚流程
+     *
+     * @param result 流程返回值
+     */
+    public void rollBack(ExampleResult result) {
+        flowClient.rollBack(result);
+    }
 
-        // 保存流程实例
-        R<ExampleInfo> exampleInfoSaveResult = flowClient.exampleInfoSave(exampleInfoEx);
-        Assert.eqTrue(exampleInfoSaveResult.isSuccess(), exampleInfoSaveResult.getMsg());
+    /**
+     * 缓存对象转字符串
+     *
+     * @param cacheData 缓存对象
+     * @return 缓存字符串
+     */
+    private String getCacheDataStr(Object cacheData) {
+        String cacheDataStr = "";
+        if (ObjectUtil.isNotEmpty(cacheData)) {
+            cacheDataStr = JSONObject.toJSONString(cacheData);
+        }
+        return cacheDataStr;
+    }
 
+    /**
+     * 获取流程编码
+     *
+     * @return 流程编码
+     */
+    private String getCode() {
+        String code = exampleAbstract.getCode();
+        Assert.notEmpty(code, FlowExplainConstant.CODE_EMPTY);
+        return code;
     }
 
+
 }

+ 57 - 0
hx-service-api/storage-api/src/main/java/com/fjhx/entity/stock/StockBackPlan.java

@@ -0,0 +1,57 @@
+package com.fjhx.entity.stock;
+
+import java.io.Serializable;
+import java.math.BigDecimal;
+import com.baomidou.mybatisplus.annotation.IdType;
+import java.util.Date;
+import com.baomidou.mybatisplus.annotation.Version;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.fjhx.base.BaseEntity;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+/**
+ * <p>
+ * 
+ * </p>
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+@Data
+public class StockBackPlan implements Serializable {
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * 主键id
+     */
+    @TableId(value = "id", type = IdType.ASSIGN_ID)
+    private Long id;
+
+    /**
+     * 排班物料
+     */
+    private String planMaterial;
+
+    /**
+     * 排班日期
+     */
+    private Date planTime;
+
+    /**
+     * 领料面积
+     */
+    private BigDecimal quantity;
+
+    /**
+     * 工号
+     */
+    private Long jobNo;
+
+    /**
+     * 创建时间
+     */
+    private Date createTime;
+
+}

+ 91 - 0
hx-service-api/storage-api/src/main/java/com/fjhx/entity/stock/StockBackPlanDetails.java

@@ -0,0 +1,91 @@
+package com.fjhx.entity.stock;
+
+import java.math.BigDecimal;
+import com.baomidou.mybatisplus.annotation.IdType;
+import java.util.Date;
+import com.baomidou.mybatisplus.annotation.Version;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.fjhx.base.BaseEntity;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+/**
+ * <p>
+ * 
+ * </p>
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+public class StockBackPlanDetails extends BaseEntity {
+
+
+    /**
+     * 排班物料
+     */
+    private String planMaterial;
+
+    /**
+     * 排班日期
+     */
+    private Date planTime;
+
+    /**
+     * 领料面积
+     */
+    private BigDecimal quantity;
+
+    /**
+     * 工号
+     */
+    private Long jobNo;
+
+    /**
+     * 修正面积
+     */
+    private BigDecimal correctArea;
+
+    /**
+     * 领料金额
+     */
+    private BigDecimal pickingMoney;
+
+    /**
+     * 领料数量
+     */
+    private Integer pickingNum;
+
+    /**
+     * 领料米数
+     */
+    private BigDecimal pickingMeters;
+
+    /**
+     * 领料面积
+     */
+    private BigDecimal pickingArea;
+
+    /**
+     * 退料金额
+     */
+    private BigDecimal backMoney;
+
+    /**
+     * 退料数量
+     */
+    private Integer backNum;
+
+    /**
+     * 退料米数
+     */
+    private BigDecimal backMeters;
+
+    /**
+     * 退料面积
+     */
+    private BigDecimal backArea;
+
+
+}

+ 17 - 0
hx-service-api/storage-api/src/main/java/com/fjhx/params/stock/StockBackPlanDetailsEx.java

@@ -0,0 +1,17 @@
+package com.fjhx.params.stock;
+
+import com.fjhx.entity.stock.StockBackPlanDetails;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+/**
+ * 
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+public class StockBackPlanDetailsEx extends StockBackPlanDetails {
+
+}

+ 17 - 0
hx-service-api/storage-api/src/main/java/com/fjhx/params/stock/StockBackPlanDetailsVo.java

@@ -0,0 +1,17 @@
+package com.fjhx.params.stock;
+
+import com.fjhx.entity.stock.StockBackPlanDetails;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+/**
+ * 
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+public class StockBackPlanDetailsVo extends StockBackPlanDetails {
+
+}

+ 17 - 0
hx-service-api/storage-api/src/main/java/com/fjhx/params/stock/StockBackPlanEx.java

@@ -0,0 +1,17 @@
+package com.fjhx.params.stock;
+
+import com.fjhx.entity.stock.StockBackPlan;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+/**
+ * 
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+public class StockBackPlanEx extends StockBackPlan {
+
+}

+ 17 - 0
hx-service-api/storage-api/src/main/java/com/fjhx/params/stock/StockBackPlanVo.java

@@ -0,0 +1,17 @@
+package com.fjhx.params.stock;
+
+import com.fjhx.entity.stock.StockBackPlan;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+/**
+ * 
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+@Data
+@EqualsAndHashCode(callSuper = true)
+public class StockBackPlanVo extends StockBackPlan {
+
+}

+ 5 - 5
hx-service/storage/src/main/java/com/fjhx/applet/mapper/MaterialReceiveMapper.xml

@@ -8,7 +8,7 @@
                aa.AccountNo        account,
                swd.WaterId         waterId,
                aa.ID               userId
-        from stock_waterdetial_copy1 swd
+        from stock_waterdetial swd
                  left join acc_account aa on swd.OperUserId = aa.ID
         where swd.InOutDevice = 1
           and swd.ApproveBillState = 0
@@ -16,7 +16,7 @@
     </select>
 
     <update id="updateReceive">
-        update stock_waterdetial_copy1
+        update stock_waterdetial
         <set>
             <if test="ApproveBillState neq null">
                 ApproveBillState = #{ApproveBillState}
@@ -38,7 +38,7 @@
     </update>
 
     <update id="updatePickingStatus">
-        update stock_waterdetial_copy1
+        update stock_waterdetial
         <set>
             ApproveBillState = #{checkState}
             <if test="ApproveBillState eq '2' ">
@@ -55,7 +55,7 @@
                m.Name          materialName,
                m.Code          materialCode,
                uu.RealName     realName
-        from stock_waterdetial_copy1 swd
+        from stock_waterdetial swd
                  left join material m on swd.MaterialCode = m.code
                  left join u_user uu on swd.OperUserId = uu.ID
                  left join acc_account aa on swd.OperUserId = aa.ID
@@ -65,7 +65,7 @@
 
     <select id="countNum" resultType="java.lang.Integer">
         select count(0)
-        from stock_waterdetial_copy1 swd
+        from stock_waterdetial swd
                  inner join acc_account aa on swd.OperUserId = aa.ID
         where swd.PickingStatus = 2
           and aa.AccountNo = #{account}

+ 17 - 15
hx-service/storage/src/main/java/com/fjhx/applet/service/impl/MaterialReceiveServiceImpl.java

@@ -66,22 +66,24 @@ public class MaterialReceiveServiceImpl extends ServiceImpl<MaterialReceiveMappe
             // 获取openId
             List<String> accountList = repairList.stream()
                     .map(item -> item.get("account").toString()).distinct().collect(Collectors.toList());
-            Map<String, String> accountMap = userClient.getOpenidByAccount(accountList);
-            // 发送小程序推送
-            for (String account : accountList) {
-                String openId = accountMap.get(account);
-                if (ObjectUtil.isNotEmpty(openId)) {
-                    Integer num = baseMapper.countNum(account);
-                    WxAppletUtil.UniformSendEntity uniformSendEntity = new WxAppletUtil.UniformSendEntity();
-                    uniformSendEntity.setTouser(openId);
-                    uniformSendEntity.setTemplate_id("YQNpUJwn7kdApbkO142eIeBq4qiYRfmNlVhSg_5ZdYg");
-                    uniformSendEntity.setPage("pages/user/login");
-                    uniformSendEntity.addData("thing3", "智能仓储");
-                    uniformSendEntity.addData("thing2", num.toString());
-                    uniformSendEntity.addData("thing6", DateUtil.format(new Date(), "yyyy年MM月dd日 HH:mm"));
-                    WxAppletUtil.sendMessage(uniformSendEntity);
+//            new Thread(() -> {
+                Map<String, String> accountMap = userClient.getOpenidByAccount(accountList, "849380");
+                // 发送小程序推送
+                for (String account : accountList) {
+                    String openId = accountMap.get(account);
+                    if (ObjectUtil.isNotEmpty(openId)) {
+                        Integer num = baseMapper.countNum(account);
+                        WxAppletUtil.UniformSendEntity uniformSendEntity = new WxAppletUtil.UniformSendEntity();
+                        uniformSendEntity.setTouser(openId);
+                        uniformSendEntity.setTemplate_id("YQNpUJwn7kdApbkO142eIeBq4qiYRfmNlVhSg_5ZdYg");
+                        uniformSendEntity.setPage("pages/user/login");
+                        uniformSendEntity.addData("thing3", "智能仓储");
+                        uniformSendEntity.addData("thing2", num.toString());
+                        uniformSendEntity.addData("thing6", DateUtil.format(new Date(), "yyyy年MM月dd日 HH:mm"));
+                        WxAppletUtil.sendMessage(uniformSendEntity);
+                    }
                 }
-            }
+//            }).start();
 
             List<String> idList = repairList.stream().map(item -> item.get("id").toString()).collect(Collectors.toList());
             baseMapper.updateReceive(idList, null, 20, 2, null);

+ 34 - 0
hx-service/storage/src/main/java/com/fjhx/stock/controller/StockBackPlanController.java

@@ -0,0 +1,34 @@
+package com.fjhx.stock.controller;
+
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import org.springblade.core.tool.api.R;
+import com.fjhx.entity.stock.StockBackPlan;
+import com.fjhx.params.stock.StockBackPlanVo;
+import com.fjhx.stock.service.StockBackPlanService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+import java.util.Map;
+
+/**
+ * <p>
+ *  前端控制器
+ * </p>
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+@RestController
+@RequestMapping("/stockBackPlan")
+public class StockBackPlanController {
+
+    @Autowired
+    private StockBackPlanService stockBackPlanService;
+
+
+
+}
+

+ 56 - 0
hx-service/storage/src/main/java/com/fjhx/stock/controller/StockBackPlanDetailsController.java

@@ -0,0 +1,56 @@
+package com.fjhx.stock.controller;
+
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import org.springblade.core.tool.api.R;
+import com.fjhx.entity.stock.StockBackPlanDetails;
+import com.fjhx.params.stock.StockBackPlanDetailsVo;
+import com.fjhx.stock.service.StockBackPlanDetailsService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+import java.util.Map;
+
+/**
+ * <p>
+ *  前端控制器
+ * </p>
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+@RestController
+@RequestMapping("/stockBackPlanDetails")
+public class StockBackPlanDetailsController {
+
+    @Autowired
+    private StockBackPlanDetailsService stockBackPlanDetailsService;
+
+    @PostMapping("/page")
+    public R page(@RequestBody Map<String, String> condition){
+        Page<StockBackPlanDetails> result = stockBackPlanDetailsService.getPage(condition);
+        return R.success(result);
+    }
+
+    @PostMapping("/add")
+    public R add(@RequestBody StockBackPlanDetailsVo stockBackPlanDetailsVo){
+        stockBackPlanDetailsService.add(stockBackPlanDetailsVo);
+        return R.success();
+    }
+
+    @PostMapping("/edit")
+    public R edit(@RequestBody StockBackPlanDetailsVo stockBackPlanDetailsVo){
+        stockBackPlanDetailsService.edit(stockBackPlanDetailsVo);
+        return R.success();
+    }
+
+    @PostMapping("/delete")
+    public R delete(@RequestBody StockBackPlanDetailsVo stockBackPlanDetailsVo){
+        stockBackPlanDetailsService.delete(stockBackPlanDetailsVo);
+        return R.success();
+    }
+
+}
+

+ 16 - 0
hx-service/storage/src/main/java/com/fjhx/stock/mapper/StockBackPlanDetailsMapper.java

@@ -0,0 +1,16 @@
+package com.fjhx.stock.mapper;
+
+import com.fjhx.entity.stock.StockBackPlanDetails;
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+
+/**
+ * <p>
+ *  Mapper 接口
+ * </p>
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+public interface StockBackPlanDetailsMapper extends BaseMapper<StockBackPlanDetails> {
+
+}

+ 5 - 0
hx-service/storage/src/main/java/com/fjhx/stock/mapper/StockBackPlanDetailsMapper.xml

@@ -0,0 +1,5 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="com.fjhx.stock.mapper.StockBackPlanDetailsMapper">
+
+</mapper>

+ 35 - 0
hx-service/storage/src/main/java/com/fjhx/stock/mapper/StockBackPlanMapper.java

@@ -0,0 +1,35 @@
+package com.fjhx.stock.mapper;
+
+import com.baomidou.mybatisplus.annotation.InterceptorIgnore;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.fjhx.entity.scheduling.Scheduling;
+import com.fjhx.entity.stock.StockBackPlan;
+import org.apache.ibatis.annotations.Param;
+import org.springblade.core.tenant.annotation.TenantIgnore;
+
+import java.util.List;
+import java.util.Map;
+
+/**
+ * <p>
+ * Mapper 接口
+ * </p>
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+public interface StockBackPlanMapper extends BaseMapper<StockBackPlan> {
+
+    @InterceptorIgnore(tenantLine = "1")
+    @TenantIgnore
+    List<Map<String, Object>> getList(@Param("ew") LambdaQueryWrapper<Scheduling> wrapper);
+
+    @TenantIgnore
+    List<Map<String, Object>> getWater(@Param("ew") QueryWrapper<Object> wrapper);
+
+    @TenantIgnore
+    List<Map<String, Object>> getCorrect(@Param("ew") QueryWrapper<Object> wrapper);
+
+}

+ 56 - 0
hx-service/storage/src/main/java/com/fjhx/stock/mapper/StockBackPlanMapper.xml

@@ -0,0 +1,56 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="com.fjhx.stock.mapper.StockBackPlanMapper">
+
+    <select id="getList" resultType="java.util.Map">
+        select t.jobNo,
+               (t.quantity * m.Width / 100) quantity,
+               t.planDate,
+               m.Name                       materialName
+        from (
+                 (
+                     select ss.printer           jobNo,
+                            ss.material_code     materialCode,
+                            ss.material_quantity quantity,
+                            ss.plan_date         planDate
+                     from stock_scheduling ss
+                         ${ew.customSqlSegment}
+                 )
+                 union all
+                 (
+                     select ss.paper_man      jobNo,
+                            ss.paper_code     materialCode,
+                            ss.paper_quantity quantity,
+                            ss.plan_date      planDate
+                     from stock_scheduling ss
+                         ${ew.customSqlSegment}
+                 )
+             ) t
+                 inner join material m on m.code = t.materialCode
+    </select>
+
+    <select id="getWater" resultType="java.util.Map">
+        select swd.ChangeNum   changeNum,
+               m.Name          materialName,
+               swd.CreatedTime createTime,
+               m.Price         price,
+               m.Width         width,
+               uu.JobNo        jobNo
+        from stock_waterdetial swd
+                 left join material m on swd.MaterialCode = m.code
+                 left join u_user uu on uu.ID = swd.OperUserId
+            ${ew.customSqlSegment}
+    </select>
+
+    <select id="getCorrect" resultType="java.util.Map">
+        select sbc.correct_area correctArea,
+               m.Name           materialName,
+               sbc.correct_time createTime,
+               uu.JobNo         jobNo
+        from stock_back_correct sbc
+                 left join material m on sbc.material_id = m.ID
+                 left join u_user uu on uu.ID = sbc.user_id
+            ${ew.customSqlSegment}
+    </select>
+
+</mapper>

+ 28 - 0
hx-service/storage/src/main/java/com/fjhx/stock/service/StockBackPlanDetailsService.java

@@ -0,0 +1,28 @@
+package com.fjhx.stock.service;
+
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.fjhx.entity.stock.StockBackPlanDetails;
+import com.fjhx.params.stock.StockBackPlanDetailsVo;
+import com.fjhx.base.BaseService;
+
+import java.util.Map;
+
+/**
+ * <p>
+ *  服务类
+ * </p>
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+public interface StockBackPlanDetailsService extends BaseService<StockBackPlanDetails> {
+
+    Page<StockBackPlanDetails> getPage(Map<String, String> condition);
+
+    void add(StockBackPlanDetailsVo stockBackPlanDetailsVo);
+
+    void edit(StockBackPlanDetailsVo stockBackPlanDetailsVo);
+
+    void delete(StockBackPlanDetailsVo stockBackPlanDetailsVo);
+
+}

+ 20 - 0
hx-service/storage/src/main/java/com/fjhx/stock/service/StockBackPlanService.java

@@ -0,0 +1,20 @@
+package com.fjhx.stock.service;
+
+import com.fjhx.base.BaseService;
+import com.fjhx.entity.stock.StockBackPlan;
+
+/**
+ * <p>
+ * 服务类
+ * </p>
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+public interface StockBackPlanService extends BaseService<StockBackPlan> {
+
+    void getScheduleTask();
+
+    void statisticsScheduleDateTask();
+
+}

+ 54 - 0
hx-service/storage/src/main/java/com/fjhx/stock/service/impl/StockBackPlanDetailsServiceImpl.java

@@ -0,0 +1,54 @@
+package com.fjhx.stock.service.impl;
+
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.baomidou.mybatisplus.core.toolkit.Wrappers;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.fjhx.utils.WrapperUtil;
+import com.fjhx.entity.stock.StockBackPlanDetails;
+import com.fjhx.params.stock.StockBackPlanDetailsVo;
+import com.fjhx.stock.mapper.StockBackPlanDetailsMapper;
+import com.fjhx.stock.service.StockBackPlanDetailsService;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import org.springframework.stereotype.Service;
+
+import java.util.Map;
+
+/**
+ * <p>
+ *  服务实现类
+ * </p>
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+@Service
+public class StockBackPlanDetailsServiceImpl extends ServiceImpl<StockBackPlanDetailsMapper, StockBackPlanDetails> implements StockBackPlanDetailsService {
+
+    @Override
+    public Page<StockBackPlanDetails> getPage(Map<String, String> condition) {
+
+        QueryWrapper<StockBackPlanDetails> wrapper = Wrappers.query();
+
+        WrapperUtil.init(condition, wrapper)
+                .createTimeDesc();
+
+        Page<StockBackPlanDetails> page = page(condition, wrapper);
+        return page;
+    }
+
+    @Override
+    public void add(StockBackPlanDetailsVo stockBackPlanDetailsVo) {
+        save(stockBackPlanDetailsVo);
+    }
+
+    @Override
+    public void edit(StockBackPlanDetailsVo stockBackPlanDetailsVo) {
+        updateById(stockBackPlanDetailsVo);
+    }
+
+    @Override
+    public void delete(StockBackPlanDetailsVo stockBackPlanDetailsVo) {
+        removeById(stockBackPlanDetailsVo.getId());
+    }
+
+}

+ 325 - 0
hx-service/storage/src/main/java/com/fjhx/stock/service/impl/StockBackPlanServiceImpl.java

@@ -0,0 +1,325 @@
+package com.fjhx.stock.service.impl;
+
+import cn.hutool.core.date.DateUtil;
+import cn.hutool.core.util.ObjectUtil;
+import com.alibaba.fastjson.JSONObject;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.baomidou.mybatisplus.core.toolkit.Wrappers;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.fjhx.entity.scheduling.Scheduling;
+import com.fjhx.entity.stock.StockBackPlan;
+import com.fjhx.entity.stock.StockBackPlanDetails;
+import com.fjhx.stock.mapper.StockBackPlanMapper;
+import com.fjhx.stock.service.StockBackPlanDetailsService;
+import com.fjhx.stock.service.StockBackPlanService;
+import com.fjhx.utils.BigDecimalUtil;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import org.springframework.web.client.RestTemplate;
+
+import java.math.BigDecimal;
+import java.util.*;
+import java.util.stream.Collectors;
+
+/**
+ * <p>
+ * 服务实现类
+ * </p>
+ *
+ * @author ${author}
+ * @since 2022-09-02
+ */
+@Service
+public class StockBackPlanServiceImpl extends ServiceImpl<StockBackPlanMapper, StockBackPlan> implements StockBackPlanService {
+
+    private static final RestTemplate restTemplate = new RestTemplate();
+
+    @Autowired
+    private StockBackPlanDetailsService stockBackPlanDetailsService;
+
+    @Override
+    public synchronized void getScheduleTask() {
+
+        // 请求v3接口获取token
+        String token = getToken();
+
+        // 请求v3接口获取所有人领料信息
+        Date date = new Date();
+
+        String beginDate = DateUtil.format(DateUtil.offsetDay(date, -4), "yyyy-MM-dd 00:00:00");
+        String endDate = DateUtil.format(date, "yyyy-MM-dd 23:59:59");
+
+        String url = "http://mes.cfmfactory.com:8087/MesWeb/planPersonOutAction.do?action=list&beginDate="
+                + beginDate + "&endDate=" + endDate + "&access_token=" + token;
+
+        String resultStr = restTemplate.getForEntity(url, String.class).getBody();
+        JSONObject resultMap = JSONObject.parseObject(resultStr);
+        // 接收到的消息
+        List<JSONObject> items = (List<JSONObject>) resultMap.get("items");
+
+        remove(Wrappers.<StockBackPlan>lambdaQuery().between(StockBackPlan::getPlanTime, beginDate, endDate));
+
+        Map<String, StockBackPlan> flagMap = new HashMap<>();
+
+        Date newDate = new Date();
+
+        // 循环领料信息
+        items.forEach(item -> {
+            // 喷印人员工号
+            long distributor = Long.parseLong(item.get("distributor").toString());
+            // 打纸人员工号
+            long paperMan = Long.parseLong(item.get("paperMan").toString());
+            // 排班面积
+            BigDecimal plantotalsquare = new BigDecimal(item.get("plantotalsquare").toString());
+            // 物料名称
+            String material = item.get("material").toString();
+            // 排班时间
+            String planDate = item.get("planDate").toString();
+
+            // 喷印人员工号添加领料记录标记
+            addOrEditFlagMap(flagMap, distributor, plantotalsquare, planDate, material, newDate);
+
+            // 打纸人员工号添加领料记录标记
+            if (paperMan > 0) {
+                addOrEditFlagMap(flagMap, paperMan, plantotalsquare, planDate, "热转印纸", newDate);
+            }
+        });
+
+        List<Map<String, Object>> list = baseMapper.getList(Wrappers.<Scheduling>lambdaQuery()
+                .between(Scheduling::getPlanDate, beginDate, endDate));
+
+        for (Map<String, Object> map : list) {
+            Long jobNo = Long.valueOf(map.get("jobNo").toString());
+            BigDecimal quantity = BigDecimalUtil.keepDecimals(map.get("quantity"));
+            String planDate = DateUtil.format((Date) map.get("planDate"), "yyyy-MM-dd");
+            String materialName = map.get("materialName").toString().split("-")[0];
+
+            addOrEditFlagMap(flagMap, jobNo, quantity, planDate, materialName, newDate);
+        }
+
+        // 更新当天的出库单
+        saveBatch(new ArrayList<>(flagMap.values()));
+    }
+
+    @Override
+    public void statisticsScheduleDateTask() {
+
+        // 统计近3天排班
+        Date endDate = new Date();
+        Date beginDate = DateUtil.beginOfDay(DateUtil.offsetDay(endDate, -3));
+
+        List<StockBackPlan> list = list(Wrappers.<StockBackPlan>lambdaQuery()
+                .between(StockBackPlan::getPlanTime, beginDate, endDate));
+
+        // 工号,物料名称,排班时间封装成key,对象为value
+        Map<String, StockBackPlanDetails> stockBackPlanMap = list.stream().collect(Collectors.toMap(
+                item -> item.getJobNo() + item.getPlanMaterial() + item.getPlanTime(),
+                item -> {
+                    StockBackPlanDetails stockBackPlanDetails = new StockBackPlanDetails();
+                    stockBackPlanDetails.setPlanMaterial(item.getPlanMaterial());
+                    stockBackPlanDetails.setPlanTime(item.getPlanTime());
+                    stockBackPlanDetails.setQuantity(item.getQuantity());
+                    stockBackPlanDetails.setJobNo(item.getJobNo());
+                    stockBackPlanDetails.setCorrectArea(BigDecimal.ZERO);
+                    stockBackPlanDetails.setPickingMoney(BigDecimal.ZERO);
+                    stockBackPlanDetails.setPickingNum(0);
+                    stockBackPlanDetails.setPickingMeters(BigDecimal.ZERO);
+                    stockBackPlanDetails.setPickingArea(BigDecimal.ZERO);
+                    stockBackPlanDetails.setBackMoney(BigDecimal.ZERO);
+                    stockBackPlanDetails.setBackNum(0);
+                    stockBackPlanDetails.setBackMeters(BigDecimal.ZERO);
+                    stockBackPlanDetails.setBackArea(BigDecimal.ZERO);
+                    return stockBackPlanDetails;
+                }
+        ));
+
+        stockBackPlanDetailsService.remove(Wrappers.<StockBackPlanDetails>lambdaQuery()
+                .between(StockBackPlanDetails::getPlanTime, beginDate, endDate));
+
+        // 领料统计
+        QueryWrapper<Object> pickingWrapper = Wrappers.query()
+                .gt("swd.CreatedTime", DateUtil.format(beginDate, "yyyy-MM-dd 7:30:00"))
+                .in("swd.StockChangeType", 20, 23)
+                .isNotNull("uu.JobNo");
+
+        // 查询出库
+        List<Map<String, Object>> pickingList = baseMapper.getWater(pickingWrapper);
+
+        for (Map<String, Object> map : pickingList) {
+
+            // 出库时间
+            Date createTime = (Date) map.get("createTime");
+            // 时
+            int h = Integer.parseInt(DateUtil.format(createTime, "H"));
+            // 分
+            int m = Integer.parseInt(DateUtil.format(createTime, "m"));
+            // 小于7点30算前一日
+            if (h < 7 || (h == 7 && m < 30)) {
+                DateUtil.offsetDay(createTime, -1);
+            }
+
+            // 排班时间
+            Date planDate = DateUtil.beginOfDay(createTime);
+            // 工号
+            Long jobNo = Long.valueOf(map.get("jobNo").toString());
+            // 物料名称
+            String materialName = map.get("materialName").toString().split("-")[0];
+            // 数量
+            BigDecimal changeNum = BigDecimalUtil.keepDecimals(map.get("changeNum"));
+            // 单价
+            BigDecimal price = BigDecimalUtil.keepDecimals(map.get("price"));
+            // 门幅
+            BigDecimal width = BigDecimalUtil.keepDecimals(map.get("width"));
+
+            // 排班对象
+            StockBackPlanDetails stockBackPlanDetails = stockBackPlanMap.get(jobNo + materialName + planDate);
+            if (stockBackPlanDetails != null) {
+
+                // 金额
+                stockBackPlanDetails.setPickingMoney(
+                        BigDecimalUtil.init(stockBackPlanDetails.getPickingMoney()).add(price.multiply(changeNum)).getValue(2));
+
+                // 数量
+                stockBackPlanDetails.setPickingNum(stockBackPlanDetails.getPickingNum() + 1);
+
+                // 米
+                stockBackPlanDetails.setPickingMeters(stockBackPlanDetails.getPickingMeters().add(changeNum));
+
+                // 面积
+                stockBackPlanDetails.setPickingArea(stockBackPlanDetails.getPickingArea().add(
+                        BigDecimalUtil.init(changeNum).multiply(width).divide(100, 2).getValue()));
+
+            }
+        }
+
+        // 回仓统计
+        QueryWrapper<Object> backWrapper = Wrappers.query()
+                .gt("swd.CreatedTime", DateUtil.format(beginDate, "yyyy-MM-dd 8:00:00"))
+                .eq("swd.StockChangeType", 16)
+                .isNotNull("uu.JobNo");
+
+        // 查询回仓
+        List<Map<String, Object>> backList = baseMapper.getWater(backWrapper);
+
+        for (Map<String, Object> map : backList) {
+
+            // 出库时间
+            Date createTime = (Date) map.get("createTime");
+
+            // 小于8点算前一日
+            if (Integer.parseInt(DateUtil.format(createTime, "H")) < 8) {
+                DateUtil.offsetDay(createTime, -1);
+            }
+
+            // 排班时间
+            Date planDate = DateUtil.beginOfDay(createTime);
+            // 工号
+            Long jobNo = Long.valueOf(map.get("jobNo").toString());
+            // 物料名称
+            String materialName = map.get("materialName").toString().split("-")[0];
+            // 数量
+            BigDecimal changeNum = BigDecimalUtil.keepDecimals(map.get("changeNum"));
+            // 单价
+            BigDecimal price = BigDecimalUtil.keepDecimals(map.get("price"));
+            // 门幅
+            BigDecimal width = BigDecimalUtil.keepDecimals(map.get("width"));
+
+            // 排班对象
+            StockBackPlanDetails stockBackPlanDetails = stockBackPlanMap.get(jobNo + materialName + planDate);
+            if (stockBackPlanDetails != null) {
+
+                // 金额
+                stockBackPlanDetails.setBackMoney(
+                        BigDecimalUtil.init(stockBackPlanDetails.getBackMoney()).add(price.multiply(changeNum)).getValue(2));
+
+                // 数量
+                stockBackPlanDetails.setBackNum(stockBackPlanDetails.getBackNum() + 1);
+
+                // 米
+                stockBackPlanDetails.setBackMeters(stockBackPlanDetails.getBackMeters().add(changeNum));
+
+                // 面积
+                stockBackPlanDetails.setBackArea(stockBackPlanDetails.getBackArea().add(
+                        BigDecimalUtil.init(changeNum).multiply(width).divide(100, 2).getValue()));
+
+            }
+        }
+
+        // 物料修正
+
+        QueryWrapper<Object> correctWrapper = Wrappers.query()
+                .gt("swd", DateUtil.format(beginDate, "yyyy-MM-dd 8:00:00"))
+                .isNotNull("uu.JobNo");
+
+
+        List<Map<String, Object>> correctList = baseMapper.getCorrect(correctWrapper);
+        for (Map<String, Object> map : correctList) {
+
+            // 出库时间
+            Date createTime = (Date) map.get("createTime");
+
+            // 小于8点算前一日
+            if (Integer.parseInt(DateUtil.format(createTime, "H")) < 8) {
+                DateUtil.offsetDay(createTime, -1);
+            }
+
+            // 排班时间
+            Date planDate = DateUtil.beginOfDay(createTime);
+            // 工号
+            Long jobNo = Long.valueOf(map.get("jobNo").toString());
+            // 物料名称
+            String materialName = map.get("materialName").toString().split("-")[0];
+            // 数量
+            BigDecimal correctArea = BigDecimalUtil.keepDecimals(map.get("correctArea"));
+
+            // 排班对象
+            StockBackPlanDetails stockBackPlanDetails = stockBackPlanMap.get(jobNo + materialName + planDate);
+            if (stockBackPlanDetails != null) {
+                // 金额
+                stockBackPlanDetails.setCorrectArea(stockBackPlanDetails.getCorrectArea().add(correctArea));
+            }
+        }
+
+        ArrayList<StockBackPlanDetails> stockBackPlanDetails = new ArrayList<>(stockBackPlanMap.values());
+
+        stockBackPlanDetailsService.saveBatch(stockBackPlanDetails);
+
+    }
+
+    /**
+     * 获取token
+     */
+    private String getToken() {
+        String url = "http://mes.cfmfactory.com:8087/portal/getAccessTokenAction.do?AppId=1&AppSecret=a2b1c2d3";
+        String result = restTemplate.getForEntity(url, String.class).getBody();
+        if (ObjectUtil.isEmpty(result)) {
+            return null;
+        }
+        JSONObject jsonObject = JSONObject.parseObject(result);
+        return jsonObject.getString("token");
+    }
+
+    /**
+     * 赋值排班数据
+     */
+    private void addOrEditFlagMap(Map<String, StockBackPlan> flagMap, Long jobNo, BigDecimal plantotalsquare, String planDate, String material, Date date) {
+        String key = jobNo + material + planDate;
+        StockBackPlan stockBackPlan = flagMap.get(key);
+
+        if (stockBackPlan == null) {
+            stockBackPlan = new StockBackPlan();
+            stockBackPlan.setJobNo(jobNo);
+            stockBackPlan.setPlanMaterial(material.trim());
+            stockBackPlan.setPlanTime(DateUtil.parse(planDate));
+            stockBackPlan.setQuantity(plantotalsquare);
+            stockBackPlan.setCreateTime(date);
+
+            flagMap.put(key, stockBackPlan);
+        } else {
+            BigDecimal quantity = stockBackPlan.getQuantity();
+            stockBackPlan.setQuantity(quantity.add(plantotalsquare));
+        }
+
+    }
+
+}