1、新增应付明细
2、新增应收明细 3、新增异常处置 4、新增风险处置 5、新增在途追踪 6、修复业务模块bug
This commit is contained in:
+97
@@ -0,0 +1,97 @@
|
||||
/**
|
||||
* BladeX Commercial License Agreement
|
||||
* Copyright (c) 2018-2099, https://bladex.cn. All rights reserved.
|
||||
* <p>
|
||||
* Use of this software is governed by the Commercial License Agreement
|
||||
* obtained after purchasing a license from BladeX.
|
||||
* <p>
|
||||
* 1. This software is for development use only under a valid license
|
||||
* from BladeX.
|
||||
* <p>
|
||||
* 2. Redistribution of this software's source code to any third party
|
||||
* without a commercial license is strictly prohibited.
|
||||
* <p>
|
||||
* 3. Licensees may copyright their own code but cannot use segments
|
||||
* from this software for such purposes. Copyright of this software
|
||||
* remains with BladeX.
|
||||
* <p>
|
||||
* Using this software signifies agreement to this License, and the software
|
||||
* must not be used for illegal purposes.
|
||||
* <p>
|
||||
* Author: Chill Zhuang (bladejava@qq.com)
|
||||
*/
|
||||
package org.springblade.transport.controller;
|
||||
|
||||
import com.baomidou.mybatisplus.core.metadata.IPage;
|
||||
import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport;
|
||||
import io.swagger.v3.oas.annotations.Operation;
|
||||
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||
import lombok.AllArgsConstructor;
|
||||
import org.springblade.core.boot.ctrl.BladeController;
|
||||
import org.springblade.core.mp.support.Condition;
|
||||
import org.springblade.core.mp.support.Query;
|
||||
import org.springblade.core.secure.annotation.PreAuth;
|
||||
import org.springblade.core.tool.api.R;
|
||||
import org.springblade.transport.pojo.dto.ExceptionDisposalFollowRequest;
|
||||
import org.springblade.transport.pojo.vo.ExceptionDisposalVO;
|
||||
import org.springblade.transport.service.IExceptionDisposalService;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
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.RequestParam;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
/**
|
||||
* 异常处置控制器
|
||||
*
|
||||
* @author Chill
|
||||
*/
|
||||
@RestController
|
||||
@AllArgsConstructor
|
||||
@PreAuth(menu = "exception_disposal")
|
||||
@RequestMapping("/exception-disposal")
|
||||
@Tag(name = "异常处置", description = "异常处置")
|
||||
public class ExceptionDisposalController extends BladeController {
|
||||
|
||||
private final IExceptionDisposalService exceptionDisposalService;
|
||||
|
||||
@GetMapping("/list")
|
||||
@ApiOperationSupport(order = 1)
|
||||
@Operation(summary = "异常处置分页")
|
||||
public R<IPage<ExceptionDisposalVO>> list(ExceptionDisposalVO exceptionDisposal, Query query) {
|
||||
return R.data(exceptionDisposalService.selectPage(Condition.getPage(query), exceptionDisposal));
|
||||
}
|
||||
|
||||
@GetMapping("/detail")
|
||||
@ApiOperationSupport(order = 2)
|
||||
@Operation(summary = "异常处置详情")
|
||||
public R<ExceptionDisposalVO> detail(@RequestParam Long id) {
|
||||
return R.data(exceptionDisposalService.detail(id));
|
||||
}
|
||||
|
||||
@PostMapping("/follow")
|
||||
@ApiOperationSupport(order = 3)
|
||||
@Operation(summary = "异常跟进")
|
||||
public R follow(@RequestBody ExceptionDisposalFollowRequest request) {
|
||||
exceptionDisposalService.follow(request);
|
||||
return R.success("跟进成功");
|
||||
}
|
||||
|
||||
@PostMapping("/complete")
|
||||
@ApiOperationSupport(order = 4)
|
||||
@Operation(summary = "完成异常")
|
||||
public R complete(@RequestBody ExceptionDisposalFollowRequest request) {
|
||||
exceptionDisposalService.complete(request.getId());
|
||||
return R.success("完成成功");
|
||||
}
|
||||
|
||||
@PostMapping("/batch-complete")
|
||||
@ApiOperationSupport(order = 5)
|
||||
@Operation(summary = "批量完成异常")
|
||||
public R batchComplete(@RequestParam String ids) {
|
||||
exceptionDisposalService.batchComplete(ids);
|
||||
return R.success("批量完成成功");
|
||||
}
|
||||
|
||||
}
|
||||
+147
@@ -0,0 +1,147 @@
|
||||
/**
|
||||
* BladeX Commercial License Agreement
|
||||
* Copyright (c) 2018-2099, https://bladex.cn. All rights reserved.
|
||||
* <p>
|
||||
* Use of this software is governed by the Commercial License Agreement
|
||||
* obtained after purchasing a license from BladeX.
|
||||
* <p>
|
||||
* 1. This software is for development use only under a valid license
|
||||
* from BladeX.
|
||||
* <p>
|
||||
* 2. Redistribution of this software's source code to any third party
|
||||
* without a commercial license is strictly prohibited.
|
||||
* <p>
|
||||
* 3. Licensees may copyright their own code but cannot use segments
|
||||
* from this software for such purposes. Copyright of this software
|
||||
* remains with BladeX.
|
||||
* <p>
|
||||
* Using this software signifies agreement to this License, and the software
|
||||
* must not be used for illegal purposes.
|
||||
* <p>
|
||||
* Author: Chill Zhuang (bladejava@qq.com)
|
||||
*/
|
||||
package org.springblade.transport.controller;
|
||||
|
||||
import com.baomidou.mybatisplus.core.metadata.IPage;
|
||||
import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport;
|
||||
import io.swagger.v3.oas.annotations.Operation;
|
||||
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||
import lombok.AllArgsConstructor;
|
||||
import jakarta.servlet.http.HttpServletResponse;
|
||||
import org.springblade.core.boot.ctrl.BladeController;
|
||||
import org.springblade.core.excel.util.ExcelUtil;
|
||||
import org.springblade.core.mp.support.Condition;
|
||||
import org.springblade.core.mp.support.Query;
|
||||
import org.springblade.core.secure.annotation.PreAuth;
|
||||
import org.springblade.core.tool.api.R;
|
||||
import org.springblade.core.tool.utils.DateUtil;
|
||||
import org.springblade.transport.pojo.dto.ReceivablePayableGenerateRequest;
|
||||
import org.springblade.transport.pojo.dto.ReceivablePayableTransferRequest;
|
||||
import org.springblade.transport.pojo.dto.ReceivablePayableUpdateFeeRequest;
|
||||
import org.springblade.transport.pojo.vo.ReceivablePayableChangeRecordVO;
|
||||
import org.springblade.transport.pojo.vo.ReceivablePayableDetailVO;
|
||||
import org.springblade.transport.pojo.vo.ReceivablePayableFeeDetailVO;
|
||||
import org.springblade.transport.service.IReceivablePayableDetailService;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
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.RequestParam;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* 应收应付明细控制器
|
||||
*
|
||||
* @author Chill
|
||||
*/
|
||||
@RestController
|
||||
@AllArgsConstructor
|
||||
@PreAuth(menu = "receivable_payable_detail")
|
||||
@RequestMapping("/receivable-payable-detail")
|
||||
@Tag(name = "应收应付明细", description = "应收应付明细")
|
||||
public class ReceivablePayableDetailController extends BladeController {
|
||||
|
||||
private final IReceivablePayableDetailService detailService;
|
||||
|
||||
@GetMapping("/list")
|
||||
@ApiOperationSupport(order = 1)
|
||||
@Operation(summary = "应收应付明细分页")
|
||||
public R<IPage<ReceivablePayableDetailVO>> list(ReceivablePayableDetailVO query, Query pageQuery) {
|
||||
return R.data(detailService.selectPage(Condition.getPage(pageQuery), query));
|
||||
}
|
||||
|
||||
@GetMapping("/fee-detail")
|
||||
@ApiOperationSupport(order = 2)
|
||||
@Operation(summary = "费用明细")
|
||||
public R<ReceivablePayableFeeDetailVO> feeDetail(@RequestParam Long id) {
|
||||
return R.data(detailService.feeDetail(id));
|
||||
}
|
||||
|
||||
@GetMapping("/change-records")
|
||||
@ApiOperationSupport(order = 3)
|
||||
@Operation(summary = "变更记录")
|
||||
public R<IPage<ReceivablePayableChangeRecordVO>> changeRecords(Query query, @RequestParam Long detailId) {
|
||||
return R.data(detailService.changeRecords(Condition.getPage(query), detailId));
|
||||
}
|
||||
|
||||
@PostMapping("/update-fee")
|
||||
@ApiOperationSupport(order = 4)
|
||||
@Operation(summary = "更新费用")
|
||||
public R updateFee(@RequestBody ReceivablePayableUpdateFeeRequest request) {
|
||||
detailService.updateFee(request);
|
||||
return R.success("更新成功");
|
||||
}
|
||||
|
||||
@GetMapping("/transfer-candidates")
|
||||
@ApiOperationSupport(order = 5)
|
||||
@Operation(summary = "转结算候选明细")
|
||||
public R<IPage<Map<String, Object>>> transferCandidates(Query query,
|
||||
@RequestParam(required = false) String contractName,
|
||||
@RequestParam(required = false) String batchNo,
|
||||
@RequestParam(required = false) String generateStartDate,
|
||||
@RequestParam(required = false) String generateEndDate,
|
||||
@RequestParam(required = false) String settlementBillType) {
|
||||
return R.data(detailService.transferCandidates(Condition.getPage(query), contractName, batchNo,
|
||||
generateStartDate, generateEndDate, settlementBillType));
|
||||
}
|
||||
|
||||
@PostMapping("/transfer-settlement")
|
||||
@ApiOperationSupport(order = 6)
|
||||
@Operation(summary = "批量转结算")
|
||||
public R transferSettlement(@RequestBody ReceivablePayableTransferRequest request) {
|
||||
detailService.transferSettlement(request);
|
||||
return R.success("转结算成功");
|
||||
}
|
||||
|
||||
@GetMapping("/generate-waybills")
|
||||
@ApiOperationSupport(order = 7)
|
||||
@Operation(summary = "生成费用可选运单")
|
||||
public R<IPage<Map<String, Object>>> generateWaybills(Query query, ReceivablePayableGenerateRequest request) {
|
||||
return R.data(detailService.generateWaybills(Condition.getPage(query), request));
|
||||
}
|
||||
|
||||
@GetMapping("/generate-preview")
|
||||
@ApiOperationSupport(order = 8)
|
||||
@Operation(summary = "生成费用预览")
|
||||
public R<ReceivablePayableFeeDetailVO> generatePreview(Query query, ReceivablePayableGenerateRequest request) {
|
||||
return R.data(detailService.generatePreview(Condition.getPage(query), request));
|
||||
}
|
||||
|
||||
@PostMapping("/generate-fee")
|
||||
@ApiOperationSupport(order = 9)
|
||||
@Operation(summary = "确认生成费用")
|
||||
public R generateFee(@RequestBody ReceivablePayableGenerateRequest request) {
|
||||
detailService.generateFee(request);
|
||||
return R.success("生成费用成功");
|
||||
}
|
||||
|
||||
@GetMapping("/export-receivable-payable-detail")
|
||||
@ApiOperationSupport(order = 10)
|
||||
@Operation(summary = "导出应收应付明细")
|
||||
public void exportReceivablePayableDetail(ReceivablePayableDetailVO query, HttpServletResponse response) {
|
||||
IPage<ReceivablePayableDetailVO> page = detailService.selectPage(Condition.getPage(new Query()), query);
|
||||
ExcelUtil.export(response, "应收应付明细" + DateUtil.time(), "应收应付明细", page.getRecords(), ReceivablePayableDetailVO.class);
|
||||
}
|
||||
}
|
||||
+57
@@ -0,0 +1,57 @@
|
||||
package org.springblade.transport.controller;
|
||||
|
||||
import com.baomidou.mybatisplus.core.metadata.IPage;
|
||||
import io.swagger.v3.oas.annotations.Operation;
|
||||
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||
import lombok.AllArgsConstructor;
|
||||
import org.springblade.core.boot.ctrl.BladeController;
|
||||
import org.springblade.core.mp.support.Condition;
|
||||
import org.springblade.core.mp.support.Query;
|
||||
import org.springblade.core.secure.annotation.PreAuth;
|
||||
import org.springblade.core.tool.api.R;
|
||||
import org.springblade.transport.pojo.dto.RiskDisposalBatchDisposeRequest;
|
||||
import org.springblade.transport.pojo.dto.RiskDisposalDisposeRequest;
|
||||
import org.springblade.transport.pojo.vo.RiskDisposalBatchResultVO;
|
||||
import org.springblade.transport.pojo.vo.RiskDisposalVO;
|
||||
import org.springblade.transport.service.IRiskDisposalService;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
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.RequestParam;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
@RestController
|
||||
@AllArgsConstructor
|
||||
@PreAuth(menu = "risk_disposal")
|
||||
@RequestMapping("/risk-disposal")
|
||||
@Tag(name = "风险处置", description = "风险处置")
|
||||
public class RiskDisposalController extends BladeController {
|
||||
|
||||
private final IRiskDisposalService riskDisposalService;
|
||||
|
||||
@GetMapping("/list")
|
||||
@Operation(summary = "风险处置分页")
|
||||
public R<IPage<RiskDisposalVO>> list(RiskDisposalVO query, Query pageQuery) {
|
||||
return R.data(riskDisposalService.selectPage(Condition.getPage(pageQuery), query));
|
||||
}
|
||||
|
||||
@GetMapping("/detail")
|
||||
@Operation(summary = "风险处置详情")
|
||||
public R<RiskDisposalVO> detail(@RequestParam Long id) {
|
||||
return R.data(riskDisposalService.detail(id));
|
||||
}
|
||||
|
||||
@PostMapping("/dispose")
|
||||
@Operation(summary = "风险处置")
|
||||
public R dispose(@RequestBody RiskDisposalDisposeRequest request) {
|
||||
riskDisposalService.dispose(request);
|
||||
return R.success("处理成功");
|
||||
}
|
||||
|
||||
@PostMapping("/batch-dispose")
|
||||
@Operation(summary = "批量风险处置")
|
||||
public R<RiskDisposalBatchResultVO> batchDispose(@RequestBody RiskDisposalBatchDisposeRequest request) {
|
||||
return R.data(riskDisposalService.batchDispose(request));
|
||||
}
|
||||
}
|
||||
+8
@@ -46,6 +46,7 @@ import org.springblade.transport.pojo.entity.ProjectApply;
|
||||
import org.springblade.transport.pojo.entity.TransportPlan;
|
||||
import org.springblade.transport.pojo.entity.Waybill;
|
||||
import org.springblade.transport.pojo.vo.BusinessRemoveResultVO;
|
||||
import org.springblade.transport.pojo.vo.LoadingManageVO;
|
||||
import org.springblade.transport.pojo.vo.WaybillVO;
|
||||
import org.springblade.transport.service.IContractManageService;
|
||||
import org.springblade.transport.service.ICustomerArchiveService;
|
||||
@@ -204,6 +205,13 @@ public class WaybillController extends BladeController {
|
||||
return R.data(waybillService.batchComplete(ids));
|
||||
}
|
||||
|
||||
@PostMapping("/road-loading")
|
||||
@ApiOperationSupport(order = 15)
|
||||
@Operation(summary = "公路配载", description = "传入ids")
|
||||
public R<LoadingManageVO> roadLoading(@Parameter(description = "主键集合", required = true) @RequestParam String ids) {
|
||||
return R.data(waybillService.roadLoading(ids));
|
||||
}
|
||||
|
||||
private Map<String, Object> option(Long id, String nameKey, String name, String extraKey, Object extraValue) {
|
||||
Map<String, Object> option = new LinkedHashMap<>();
|
||||
option.put("id", id);
|
||||
|
||||
+36
@@ -0,0 +1,36 @@
|
||||
/**
|
||||
* BladeX Commercial License Agreement
|
||||
* Copyright (c) 2018-2099, https://bladex.cn. All rights reserved.
|
||||
* <p>
|
||||
* Use of this software is governed by the Commercial License Agreement
|
||||
* obtained after purchasing a license from BladeX.
|
||||
* <p>
|
||||
* 1. This software is for development use only under a valid license
|
||||
* from BladeX.
|
||||
* <p>
|
||||
* 2. Redistribution of this software's source code to any third party
|
||||
* without a commercial license is strictly prohibited.
|
||||
* <p>
|
||||
* 3. Licensees may copyright their own code but cannot use segments
|
||||
* from this software for such purposes. Copyright of this software
|
||||
* remains with BladeX.
|
||||
* <p>
|
||||
* Using this software signifies agreement to this License, and the software
|
||||
* must not be used for illegal purposes.
|
||||
* <p>
|
||||
* Author: Chill Zhuang (bladejava@qq.com)
|
||||
*/
|
||||
package org.springblade.transport.mapper;
|
||||
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
import org.springblade.transport.pojo.entity.ExceptionDisposalFollowRecord;
|
||||
|
||||
/**
|
||||
* 异常处置跟进记录 Mapper
|
||||
*
|
||||
* @author Chill
|
||||
*/
|
||||
@Mapper
|
||||
public interface ExceptionDisposalFollowRecordMapper extends BaseMapper<ExceptionDisposalFollowRecord> {
|
||||
}
|
||||
+36
@@ -0,0 +1,36 @@
|
||||
/**
|
||||
* BladeX Commercial License Agreement
|
||||
* Copyright (c) 2018-2099, https://bladex.cn. All rights reserved.
|
||||
* <p>
|
||||
* Use of this software is governed by the Commercial License Agreement
|
||||
* obtained after purchasing a license from BladeX.
|
||||
* <p>
|
||||
* 1. This software is for development use only under a valid license
|
||||
* from BladeX.
|
||||
* <p>
|
||||
* 2. Redistribution of this software's source code to any third party
|
||||
* without a commercial license is strictly prohibited.
|
||||
* <p>
|
||||
* 3. Licensees may copyright their own code but cannot use segments
|
||||
* from this software for such purposes. Copyright of this software
|
||||
* remains with BladeX.
|
||||
* <p>
|
||||
* Using this software signifies agreement to this License, and the software
|
||||
* must not be used for illegal purposes.
|
||||
* <p>
|
||||
* Author: Chill Zhuang (bladejava@qq.com)
|
||||
*/
|
||||
package org.springblade.transport.mapper;
|
||||
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
import org.springblade.transport.pojo.entity.ExceptionDisposal;
|
||||
|
||||
/**
|
||||
* 异常处置 Mapper
|
||||
*
|
||||
* @author Chill
|
||||
*/
|
||||
@Mapper
|
||||
public interface ExceptionDisposalMapper extends BaseMapper<ExceptionDisposal> {
|
||||
}
|
||||
+36
@@ -0,0 +1,36 @@
|
||||
/**
|
||||
* BladeX Commercial License Agreement
|
||||
* Copyright (c) 2018-2099, https://bladex.cn. All rights reserved.
|
||||
* <p>
|
||||
* Use of this software is governed by the Commercial License Agreement
|
||||
* obtained after purchasing a license from BladeX.
|
||||
* <p>
|
||||
* 1. This software is for development use only under a valid license
|
||||
* from BladeX.
|
||||
* <p>
|
||||
* 2. Redistribution of this software's source code to any third party
|
||||
* without a commercial license is strictly prohibited.
|
||||
* <p>
|
||||
* 3. Licensees may copyright their own code but cannot use segments
|
||||
* from this software for such purposes. Copyright of this software
|
||||
* remains with BladeX.
|
||||
* <p>
|
||||
* Using this software signifies agreement to this License, and the software
|
||||
* must not be used for illegal purposes.
|
||||
* <p>
|
||||
* Author: Chill Zhuang (bladejava@qq.com)
|
||||
*/
|
||||
package org.springblade.transport.mapper;
|
||||
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
import org.springblade.transport.pojo.entity.ReceivablePayableCargoFee;
|
||||
|
||||
/**
|
||||
* 应收应付货物费用 Mapper
|
||||
*
|
||||
* @author Chill
|
||||
*/
|
||||
@Mapper
|
||||
public interface ReceivablePayableCargoFeeMapper extends BaseMapper<ReceivablePayableCargoFee> {
|
||||
}
|
||||
+36
@@ -0,0 +1,36 @@
|
||||
/**
|
||||
* BladeX Commercial License Agreement
|
||||
* Copyright (c) 2018-2099, https://bladex.cn. All rights reserved.
|
||||
* <p>
|
||||
* Use of this software is governed by the Commercial License Agreement
|
||||
* obtained after purchasing a license from BladeX.
|
||||
* <p>
|
||||
* 1. This software is for development use only under a valid license
|
||||
* from BladeX.
|
||||
* <p>
|
||||
* 2. Redistribution of this software's source code to any third party
|
||||
* without a commercial license is strictly prohibited.
|
||||
* <p>
|
||||
* 3. Licensees may copyright their own code but cannot use segments
|
||||
* from this software for such purposes. Copyright of this software
|
||||
* remains with BladeX.
|
||||
* <p>
|
||||
* Using this software signifies agreement to this License, and the software
|
||||
* must not be used for illegal purposes.
|
||||
* <p>
|
||||
* Author: Chill Zhuang (bladejava@qq.com)
|
||||
*/
|
||||
package org.springblade.transport.mapper;
|
||||
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
import org.springblade.transport.pojo.entity.ReceivablePayableChangeRecord;
|
||||
|
||||
/**
|
||||
* 应收应付变更记录 Mapper
|
||||
*
|
||||
* @author Chill
|
||||
*/
|
||||
@Mapper
|
||||
public interface ReceivablePayableChangeRecordMapper extends BaseMapper<ReceivablePayableChangeRecord> {
|
||||
}
|
||||
+36
@@ -0,0 +1,36 @@
|
||||
/**
|
||||
* BladeX Commercial License Agreement
|
||||
* Copyright (c) 2018-2099, https://bladex.cn. All rights reserved.
|
||||
* <p>
|
||||
* Use of this software is governed by the Commercial License Agreement
|
||||
* obtained after purchasing a license from BladeX.
|
||||
* <p>
|
||||
* 1. This software is for development use only under a valid license
|
||||
* from BladeX.
|
||||
* <p>
|
||||
* 2. Redistribution of this software's source code to any third party
|
||||
* without a commercial license is strictly prohibited.
|
||||
* <p>
|
||||
* 3. Licensees may copyright their own code but cannot use segments
|
||||
* from this software for such purposes. Copyright of this software
|
||||
* remains with BladeX.
|
||||
* <p>
|
||||
* Using this software signifies agreement to this License, and the software
|
||||
* must not be used for illegal purposes.
|
||||
* <p>
|
||||
* Author: Chill Zhuang (bladejava@qq.com)
|
||||
*/
|
||||
package org.springblade.transport.mapper;
|
||||
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
import org.springblade.transport.pojo.entity.ReceivablePayableDetail;
|
||||
|
||||
/**
|
||||
* 应收应付明细 Mapper
|
||||
*
|
||||
* @author Chill
|
||||
*/
|
||||
@Mapper
|
||||
public interface ReceivablePayableDetailMapper extends BaseMapper<ReceivablePayableDetail> {
|
||||
}
|
||||
+9
@@ -0,0 +1,9 @@
|
||||
package org.springblade.transport.mapper;
|
||||
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
import org.springblade.transport.pojo.entity.RiskDisposal;
|
||||
|
||||
@Mapper
|
||||
public interface RiskDisposalMapper extends BaseMapper<RiskDisposal> {
|
||||
}
|
||||
+48
@@ -0,0 +1,48 @@
|
||||
/**
|
||||
* BladeX Commercial License Agreement
|
||||
* Copyright (c) 2018-2099, https://bladex.cn. All rights reserved.
|
||||
* <p>
|
||||
* Use of this software is governed by the Commercial License Agreement
|
||||
* obtained after purchasing a license from BladeX.
|
||||
* <p>
|
||||
* 1. This software is for development use only under a valid license
|
||||
* from BladeX.
|
||||
* <p>
|
||||
* 2. Redistribution of this software's source code to any third party
|
||||
* without a commercial license is strictly prohibited.
|
||||
* <p>
|
||||
* 3. Licensees may copyright their own code but cannot use segments
|
||||
* from this software for such purposes. Copyright of this software
|
||||
* remains with BladeX.
|
||||
* <p>
|
||||
* Using this software signifies agreement to this License, and the software
|
||||
* must not be used for illegal purposes.
|
||||
* <p>
|
||||
* Author: Chill Zhuang (bladejava@qq.com)
|
||||
*/
|
||||
package org.springblade.transport.service;
|
||||
|
||||
import com.baomidou.mybatisplus.core.metadata.IPage;
|
||||
import org.springblade.core.mp.base.BaseService;
|
||||
import org.springblade.transport.pojo.dto.ExceptionDisposalFollowRequest;
|
||||
import org.springblade.transport.pojo.entity.ExceptionDisposal;
|
||||
import org.springblade.transport.pojo.vo.ExceptionDisposalVO;
|
||||
|
||||
/**
|
||||
* 异常处置服务
|
||||
*
|
||||
* @author Chill
|
||||
*/
|
||||
public interface IExceptionDisposalService extends BaseService<ExceptionDisposal> {
|
||||
|
||||
IPage<ExceptionDisposalVO> selectPage(IPage<ExceptionDisposal> page, ExceptionDisposalVO query);
|
||||
|
||||
ExceptionDisposalVO detail(Long id);
|
||||
|
||||
void follow(ExceptionDisposalFollowRequest request);
|
||||
|
||||
void complete(Long id);
|
||||
|
||||
void batchComplete(String ids);
|
||||
|
||||
}
|
||||
+62
@@ -0,0 +1,62 @@
|
||||
/**
|
||||
* BladeX Commercial License Agreement
|
||||
* Copyright (c) 2018-2099, https://bladex.cn. All rights reserved.
|
||||
* <p>
|
||||
* Use of this software is governed by the Commercial License Agreement
|
||||
* obtained after purchasing a license from BladeX.
|
||||
* <p>
|
||||
* 1. This software is for development use only under a valid license
|
||||
* from BladeX.
|
||||
* <p>
|
||||
* 2. Redistribution of this software's source code to any third party
|
||||
* without a commercial license is strictly prohibited.
|
||||
* <p>
|
||||
* 3. Licensees may copyright their own code but cannot use segments
|
||||
* from this software for such purposes. Copyright of this software
|
||||
* remains with BladeX.
|
||||
* <p>
|
||||
* Using this software signifies agreement to this License, and the software
|
||||
* must not be used for illegal purposes.
|
||||
* <p>
|
||||
* Author: Chill Zhuang (bladejava@qq.com)
|
||||
*/
|
||||
package org.springblade.transport.service;
|
||||
|
||||
import com.baomidou.mybatisplus.core.metadata.IPage;
|
||||
import org.springblade.core.mp.base.BaseService;
|
||||
import org.springblade.transport.pojo.dto.ReceivablePayableGenerateRequest;
|
||||
import org.springblade.transport.pojo.dto.ReceivablePayableTransferRequest;
|
||||
import org.springblade.transport.pojo.dto.ReceivablePayableUpdateFeeRequest;
|
||||
import org.springblade.transport.pojo.entity.ReceivablePayableDetail;
|
||||
import org.springblade.transport.pojo.vo.ReceivablePayableChangeRecordVO;
|
||||
import org.springblade.transport.pojo.vo.ReceivablePayableDetailVO;
|
||||
import org.springblade.transport.pojo.vo.ReceivablePayableFeeDetailVO;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* 应收应付明细服务
|
||||
*
|
||||
* @author Chill
|
||||
*/
|
||||
public interface IReceivablePayableDetailService extends BaseService<ReceivablePayableDetail> {
|
||||
|
||||
IPage<ReceivablePayableDetailVO> selectPage(IPage<ReceivablePayableDetail> page, ReceivablePayableDetailVO query);
|
||||
|
||||
ReceivablePayableFeeDetailVO feeDetail(Long id);
|
||||
|
||||
IPage<ReceivablePayableChangeRecordVO> changeRecords(IPage<?> page, Long detailId);
|
||||
|
||||
void updateFee(ReceivablePayableUpdateFeeRequest request);
|
||||
|
||||
void transferSettlement(ReceivablePayableTransferRequest request);
|
||||
|
||||
IPage<Map<String, Object>> transferCandidates(IPage<?> page, String contractName, String batchNo,
|
||||
String generateStartDate, String generateEndDate, String settlementBillType);
|
||||
|
||||
IPage<Map<String, Object>> generateWaybills(IPage<?> page, ReceivablePayableGenerateRequest request);
|
||||
|
||||
ReceivablePayableFeeDetailVO generatePreview(IPage<?> page, ReceivablePayableGenerateRequest request);
|
||||
|
||||
void generateFee(ReceivablePayableGenerateRequest request);
|
||||
}
|
||||
+21
@@ -0,0 +1,21 @@
|
||||
package org.springblade.transport.service;
|
||||
|
||||
import com.baomidou.mybatisplus.core.metadata.IPage;
|
||||
import org.springblade.core.mp.base.BaseService;
|
||||
import org.springblade.transport.pojo.dto.RiskDisposalBatchDisposeRequest;
|
||||
import org.springblade.transport.pojo.dto.RiskDisposalDisposeRequest;
|
||||
import org.springblade.transport.pojo.entity.RiskDisposal;
|
||||
import org.springblade.transport.pojo.vo.RiskDisposalBatchResultVO;
|
||||
import org.springblade.transport.pojo.vo.RiskDisposalVO;
|
||||
|
||||
public interface IRiskDisposalService extends BaseService<RiskDisposal> {
|
||||
|
||||
IPage<RiskDisposalVO> selectPage(IPage<RiskDisposal> page, RiskDisposalVO query);
|
||||
|
||||
RiskDisposalVO detail(Long id);
|
||||
|
||||
void dispose(RiskDisposalDisposeRequest request);
|
||||
|
||||
RiskDisposalBatchResultVO batchDispose(RiskDisposalBatchDisposeRequest request);
|
||||
|
||||
}
|
||||
+2
@@ -27,6 +27,7 @@ import org.springblade.core.mp.base.BaseService;
|
||||
import org.springblade.transport.excel.WaybillExcel;
|
||||
import org.springblade.transport.pojo.entity.Waybill;
|
||||
import org.springblade.transport.pojo.vo.BusinessRemoveResultVO;
|
||||
import org.springblade.transport.pojo.vo.LoadingManageVO;
|
||||
import org.springblade.transport.pojo.vo.WaybillVO;
|
||||
|
||||
import java.util.List;
|
||||
@@ -49,5 +50,6 @@ public interface IWaybillService extends BaseService<Waybill> {
|
||||
boolean reassign(Long id);
|
||||
boolean complete(Long id);
|
||||
BusinessRemoveResultVO batchComplete(String ids);
|
||||
LoadingManageVO roadLoading(String ids);
|
||||
|
||||
}
|
||||
|
||||
+203
@@ -0,0 +1,203 @@
|
||||
/**
|
||||
* BladeX Commercial License Agreement
|
||||
* Copyright (c) 2018-2099, https://bladex.cn. All rights reserved.
|
||||
* <p>
|
||||
* Use of this software is governed by the Commercial License Agreement
|
||||
* obtained after purchasing a license from BladeX.
|
||||
* <p>
|
||||
* 1. This software is for development use only under a valid license
|
||||
* from BladeX.
|
||||
* <p>
|
||||
* 2. Redistribution of this software's source code to any third party
|
||||
* without a commercial license is strictly prohibited.
|
||||
* <p>
|
||||
* 3. Licensees may copyright their own code but cannot use segments
|
||||
* from this software for such purposes. Copyright of this software
|
||||
* remains with BladeX.
|
||||
* <p>
|
||||
* Using this software signifies agreement to this License, and the software
|
||||
* must not be used for illegal purposes.
|
||||
* <p>
|
||||
* Author: Chill Zhuang (bladejava@qq.com)
|
||||
*/
|
||||
package org.springblade.transport.service.impl;
|
||||
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.core.metadata.IPage;
|
||||
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
|
||||
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||
import org.springblade.core.log.exception.ServiceException;
|
||||
import org.springblade.core.mp.base.BaseServiceImpl;
|
||||
import org.springblade.core.secure.utils.AuthUtil;
|
||||
import org.springblade.core.tool.utils.BeanUtil;
|
||||
import org.springblade.core.tool.utils.Func;
|
||||
import org.springblade.system.cache.UserCache;
|
||||
import org.springblade.transport.mapper.ExceptionDisposalFollowRecordMapper;
|
||||
import org.springblade.transport.mapper.ExceptionDisposalMapper;
|
||||
import org.springblade.transport.pojo.dto.ExceptionDisposalFollowRequest;
|
||||
import org.springblade.transport.pojo.entity.ExceptionDisposal;
|
||||
import org.springblade.transport.pojo.entity.ExceptionDisposalFollowRecord;
|
||||
import org.springblade.transport.pojo.vo.ExceptionDisposalFollowRecordVO;
|
||||
import org.springblade.transport.pojo.vo.ExceptionDisposalVO;
|
||||
import org.springblade.transport.service.IExceptionDisposalService;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
import java.time.LocalDateTime;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
|
||||
/**
|
||||
* 异常处置服务实现类
|
||||
*
|
||||
* @author Chill
|
||||
*/
|
||||
@Service
|
||||
public class ExceptionDisposalServiceImpl
|
||||
extends BaseServiceImpl<ExceptionDisposalMapper, ExceptionDisposal>
|
||||
implements IExceptionDisposalService {
|
||||
|
||||
private static final String STATUS_PENDING = "pending";
|
||||
private static final String STATUS_PROCESSING = "processing";
|
||||
private static final String STATUS_COMPLETED = "completed";
|
||||
|
||||
private final ExceptionDisposalFollowRecordMapper followRecordMapper;
|
||||
|
||||
public ExceptionDisposalServiceImpl(ExceptionDisposalFollowRecordMapper followRecordMapper) {
|
||||
this.followRecordMapper = followRecordMapper;
|
||||
}
|
||||
|
||||
@Override
|
||||
public IPage<ExceptionDisposalVO> selectPage(IPage<ExceptionDisposal> page, ExceptionDisposalVO query) {
|
||||
IPage<ExceptionDisposal> entityPage = page(page, buildQuery(query));
|
||||
Page<ExceptionDisposalVO> voPage = new Page<>(entityPage.getCurrent(), entityPage.getSize(), entityPage.getTotal());
|
||||
voPage.setRecords(entityPage.getRecords().stream().map(this::toVO).toList());
|
||||
return voPage;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ExceptionDisposalVO detail(Long id) {
|
||||
ExceptionDisposalVO vo = toVO(getExisting(id));
|
||||
vo.setFollowRecords(followRecords(id));
|
||||
return vo;
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void follow(ExceptionDisposalFollowRequest request) {
|
||||
if (request == null || request.getId() == null) {
|
||||
throw new ServiceException("请选择需要跟进的异常");
|
||||
}
|
||||
if (Func.isBlank(request.getFollowContent())) {
|
||||
throw new ServiceException("请填写跟进说明");
|
||||
}
|
||||
if (request.getFollowContent().length() > 500) {
|
||||
throw new ServiceException("跟进说明不能超过500字");
|
||||
}
|
||||
ExceptionDisposal disposal = getExisting(request.getId());
|
||||
if (STATUS_COMPLETED.equals(disposal.getDisposalStatus())) {
|
||||
throw new ServiceException("已完成的异常不允许继续跟进");
|
||||
}
|
||||
disposal.setDisposalStatus(STATUS_PROCESSING);
|
||||
disposal.setLatestFollowContent(request.getFollowContent());
|
||||
updateById(disposal);
|
||||
|
||||
ExceptionDisposalFollowRecord record = new ExceptionDisposalFollowRecord();
|
||||
record.setDisposalId(disposal.getId());
|
||||
record.setFollowContent(request.getFollowContent());
|
||||
record.setFollowUser(AuthUtil.getUserId());
|
||||
record.setFollowUserName(UserCache.getUserRealName(AuthUtil.getUserId()));
|
||||
record.setFollowTime(LocalDateTime.now());
|
||||
followRecordMapper.insert(record);
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void complete(Long id) {
|
||||
ExceptionDisposal disposal = getExisting(id);
|
||||
if (STATUS_COMPLETED.equals(disposal.getDisposalStatus())) {
|
||||
throw new ServiceException("异常已完成,请勿重复操作");
|
||||
}
|
||||
disposal.setDisposalStatus(STATUS_COMPLETED);
|
||||
updateById(disposal);
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void batchComplete(String ids) {
|
||||
if (Func.isBlank(ids)) {
|
||||
throw new ServiceException("请选择需要完成的异常");
|
||||
}
|
||||
List<Long> idList = Func.toLongList(ids);
|
||||
if (Func.isEmpty(idList)) {
|
||||
throw new ServiceException("请选择需要完成的异常");
|
||||
}
|
||||
List<ExceptionDisposal> disposals = listByIds(idList);
|
||||
if (disposals.size() != idList.size()) {
|
||||
throw new ServiceException("存在无效的异常记录");
|
||||
}
|
||||
for (ExceptionDisposal disposal : disposals) {
|
||||
if (STATUS_COMPLETED.equals(disposal.getDisposalStatus())) {
|
||||
throw new ServiceException("已完成的异常不允许重复完成");
|
||||
}
|
||||
disposal.setDisposalStatus(STATUS_COMPLETED);
|
||||
}
|
||||
updateBatchById(disposals);
|
||||
}
|
||||
|
||||
private LambdaQueryWrapper<ExceptionDisposal> buildQuery(ExceptionDisposalVO query) {
|
||||
LambdaQueryWrapper<ExceptionDisposal> wrapper = Wrappers.<ExceptionDisposal>lambdaQuery()
|
||||
.eq(ExceptionDisposal::getIsDeleted, 0)
|
||||
.like(Func.isNotEmpty(query.getWaybillNo()), ExceptionDisposal::getWaybillNo, query.getWaybillNo())
|
||||
.like(Func.isNotEmpty(query.getVehicleNo()), ExceptionDisposal::getVehicleNo, query.getVehicleNo())
|
||||
.like(Func.isNotEmpty(query.getReporterName()), ExceptionDisposal::getReporterName, query.getReporterName())
|
||||
.ge(query.getReportStartTime() != null, ExceptionDisposal::getReportTime, query.getReportStartTime())
|
||||
.le(query.getReportEndTime() != null, ExceptionDisposal::getReportTime, query.getReportEndTime())
|
||||
.like(Func.isNotEmpty(query.getProjectName()), ExceptionDisposal::getProjectName, query.getProjectName())
|
||||
.like(Func.isNotEmpty(query.getCarrierName()), ExceptionDisposal::getCarrierName, query.getCarrierName())
|
||||
.eq(Func.isNotEmpty(query.getExceptionType()), ExceptionDisposal::getExceptionType, query.getExceptionType())
|
||||
.eq(Func.isNotEmpty(query.getDisposalStatus()), ExceptionDisposal::getDisposalStatus, query.getDisposalStatus());
|
||||
return wrapper.orderByDesc(ExceptionDisposal::getCreateTime);
|
||||
}
|
||||
|
||||
private ExceptionDisposal getExisting(Long id) {
|
||||
if (id == null) {
|
||||
throw new ServiceException("异常记录不存在");
|
||||
}
|
||||
ExceptionDisposal disposal = getById(id);
|
||||
if (disposal == null || Objects.equals(disposal.getIsDeleted(), 1)) {
|
||||
throw new ServiceException("异常记录不存在");
|
||||
}
|
||||
return disposal;
|
||||
}
|
||||
|
||||
private ExceptionDisposalVO toVO(ExceptionDisposal entity) {
|
||||
ExceptionDisposalVO vo = BeanUtil.copyProperties(entity, ExceptionDisposalVO.class);
|
||||
if (vo == null) {
|
||||
return null;
|
||||
}
|
||||
vo.setCreateUserName(UserCache.getUserRealName(entity.getCreateUser()));
|
||||
vo.setUpdateUserName(UserCache.getUserRealName(entity.getUpdateUser()));
|
||||
vo.setDisposalStatusName(statusName(entity.getDisposalStatus()));
|
||||
return vo;
|
||||
}
|
||||
|
||||
private List<ExceptionDisposalFollowRecordVO> followRecords(Long id) {
|
||||
List<ExceptionDisposalFollowRecord> records = followRecordMapper.selectList(Wrappers.<ExceptionDisposalFollowRecord>lambdaQuery()
|
||||
.eq(ExceptionDisposalFollowRecord::getDisposalId, id)
|
||||
.eq(ExceptionDisposalFollowRecord::getIsDeleted, 0)
|
||||
.orderByDesc(ExceptionDisposalFollowRecord::getFollowTime));
|
||||
return records.stream().map(record -> Objects.requireNonNull(
|
||||
BeanUtil.copyProperties(record, ExceptionDisposalFollowRecordVO.class))).toList();
|
||||
}
|
||||
|
||||
private String statusName(String status) {
|
||||
return switch (Func.toStr(status)) {
|
||||
case STATUS_PENDING -> "待处理";
|
||||
case STATUS_PROCESSING -> "处理中";
|
||||
case STATUS_COMPLETED -> "已完成";
|
||||
default -> "";
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
+532
@@ -0,0 +1,532 @@
|
||||
/**
|
||||
* BladeX Commercial License Agreement
|
||||
* Copyright (c) 2018-2099, https://bladex.cn. All rights reserved.
|
||||
* <p>
|
||||
* Use of this software is governed by the Commercial License Agreement
|
||||
* obtained after purchasing a license from BladeX.
|
||||
* <p>
|
||||
* 1. This software is for development use only under a valid license
|
||||
* from BladeX.
|
||||
* <p>
|
||||
* 2. Redistribution of this software's source code to any third party
|
||||
* without a commercial license is strictly prohibited.
|
||||
* <p>
|
||||
* 3. Licensees may copyright their own code but cannot use segments
|
||||
* from this software for such purposes. Copyright of this software
|
||||
* remains with BladeX.
|
||||
* <p>
|
||||
* Using this software signifies agreement to this License, and the software
|
||||
* must not be used for illegal purposes.
|
||||
* <p>
|
||||
* Author: Chill Zhuang (bladejava@qq.com)
|
||||
*/
|
||||
package org.springblade.transport.service.impl;
|
||||
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.core.metadata.IPage;
|
||||
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
|
||||
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||
import org.springblade.core.log.exception.ServiceException;
|
||||
import org.springblade.core.mp.base.BaseServiceImpl;
|
||||
import org.springblade.core.secure.utils.AuthUtil;
|
||||
import org.springblade.core.tool.jackson.JsonUtil;
|
||||
import org.springblade.core.tool.utils.BeanUtil;
|
||||
import org.springblade.core.tool.utils.Func;
|
||||
import org.springblade.system.cache.UserCache;
|
||||
import org.springblade.transport.mapper.ReceivablePayableCargoFeeMapper;
|
||||
import org.springblade.transport.mapper.ReceivablePayableChangeRecordMapper;
|
||||
import org.springblade.transport.mapper.ReceivablePayableDetailMapper;
|
||||
import org.springblade.transport.pojo.dto.ReceivablePayableGenerateRequest;
|
||||
import org.springblade.transport.pojo.dto.ReceivablePayableTransferRequest;
|
||||
import org.springblade.transport.pojo.dto.ReceivablePayableUpdateFeeRequest;
|
||||
import org.springblade.transport.pojo.entity.ContractManage;
|
||||
import org.springblade.transport.pojo.entity.ReceivablePayableCargoFee;
|
||||
import org.springblade.transport.pojo.entity.ReceivablePayableChangeRecord;
|
||||
import org.springblade.transport.pojo.entity.ReceivablePayableDetail;
|
||||
import org.springblade.transport.pojo.entity.Waybill;
|
||||
import org.springblade.transport.pojo.vo.ReceivablePayableCargoFeeVO;
|
||||
import org.springblade.transport.pojo.vo.ReceivablePayableChangeRecordVO;
|
||||
import org.springblade.transport.pojo.vo.ReceivablePayableDetailVO;
|
||||
import org.springblade.transport.pojo.vo.ReceivablePayableFeeDetailVO;
|
||||
import org.springblade.transport.service.IContractManageService;
|
||||
import org.springblade.transport.service.IReceivablePayableDetailService;
|
||||
import org.springblade.transport.service.IWaybillService;
|
||||
import org.springblade.transport.wrapper.ReceivablePayableDetailWrapper;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.math.RoundingMode;
|
||||
import java.time.LocalDate;
|
||||
import java.time.LocalDateTime;
|
||||
import java.time.format.DateTimeFormatter;
|
||||
import java.util.ArrayList;
|
||||
import java.util.LinkedHashMap;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* 应收应付明细服务实现类
|
||||
*
|
||||
* @author Chill
|
||||
*/
|
||||
@Service
|
||||
public class ReceivablePayableDetailServiceImpl
|
||||
extends BaseServiceImpl<ReceivablePayableDetailMapper, ReceivablePayableDetail>
|
||||
implements IReceivablePayableDetailService {
|
||||
|
||||
private final ReceivablePayableCargoFeeMapper cargoFeeMapper;
|
||||
private final ReceivablePayableChangeRecordMapper changeRecordMapper;
|
||||
private final IWaybillService waybillService;
|
||||
private final IContractManageService contractManageService;
|
||||
|
||||
public ReceivablePayableDetailServiceImpl(ReceivablePayableCargoFeeMapper cargoFeeMapper,
|
||||
ReceivablePayableChangeRecordMapper changeRecordMapper,
|
||||
IWaybillService waybillService,
|
||||
IContractManageService contractManageService) {
|
||||
this.cargoFeeMapper = cargoFeeMapper;
|
||||
this.changeRecordMapper = changeRecordMapper;
|
||||
this.waybillService = waybillService;
|
||||
this.contractManageService = contractManageService;
|
||||
}
|
||||
|
||||
@Override
|
||||
public IPage<ReceivablePayableDetailVO> selectPage(IPage<ReceivablePayableDetail> page, ReceivablePayableDetailVO query) {
|
||||
return ReceivablePayableDetailWrapper.build().pageVO(page(page, buildQuery(query)));
|
||||
}
|
||||
|
||||
@Override
|
||||
public ReceivablePayableFeeDetailVO feeDetail(Long id) {
|
||||
ReceivablePayableDetail detail = getExisting(id);
|
||||
List<ReceivablePayableCargoFee> rows = cargoFeeMapper.selectList(Wrappers.<ReceivablePayableCargoFee>lambdaQuery()
|
||||
.eq(ReceivablePayableCargoFee::getDetailId, detail.getId())
|
||||
.eq(ReceivablePayableCargoFee::getIsDeleted, 0)
|
||||
.orderByAsc(ReceivablePayableCargoFee::getCreateTime));
|
||||
return buildFeeDetail(rows);
|
||||
}
|
||||
|
||||
@Override
|
||||
public IPage<ReceivablePayableChangeRecordVO> changeRecords(IPage<?> page, Long detailId) {
|
||||
LambdaQueryWrapper<ReceivablePayableChangeRecord> wrapper = Wrappers.<ReceivablePayableChangeRecord>lambdaQuery()
|
||||
.eq(ReceivablePayableChangeRecord::getDetailId, detailId)
|
||||
.eq(ReceivablePayableChangeRecord::getIsDeleted, 0)
|
||||
.orderByDesc(ReceivablePayableChangeRecord::getAdjustTime);
|
||||
IPage<ReceivablePayableChangeRecord> entityPage = changeRecordMapper.selectPage(new Page<>(page.getCurrent(), page.getSize()), wrapper);
|
||||
Page<ReceivablePayableChangeRecordVO> voPage = new Page<>(entityPage.getCurrent(), entityPage.getSize(), entityPage.getTotal());
|
||||
voPage.setRecords(entityPage.getRecords().stream().map(record -> Objects.requireNonNull(
|
||||
BeanUtil.copyProperties(record, ReceivablePayableChangeRecordVO.class))).toList());
|
||||
return voPage;
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void updateFee(ReceivablePayableUpdateFeeRequest request) {
|
||||
if (Boolean.TRUE.equals(request.getCloseOnly())) {
|
||||
closeDetails(request.getIds());
|
||||
return;
|
||||
}
|
||||
if (Func.isEmpty(request.getIds()) && Func.isEmpty(request.getContractId())) {
|
||||
throw new ServiceException("请选择需要更新的费用明细或合同");
|
||||
}
|
||||
List<ReceivablePayableDetail> details = list(buildUpdateQuery(request));
|
||||
if (Func.isEmpty(details)) {
|
||||
throw new ServiceException("没有可更新的待结算明细");
|
||||
}
|
||||
for (ReceivablePayableDetail detail : details) {
|
||||
if (!"pending".equals(detail.getSettlementStatus())) {
|
||||
continue;
|
||||
}
|
||||
BigDecimal before = money(detail.getTotalAmount());
|
||||
rebuildDetailFee(detail);
|
||||
saveChangeRecord(detail, "【费用合计】从[" + formatMoney(before) + "]调整为[" + formatMoney(detail.getTotalAmount()) + "]",
|
||||
request.getAdjustReason());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void transferSettlement(ReceivablePayableTransferRequest request) {
|
||||
if (Func.isEmpty(request.getIds())) {
|
||||
throw new ServiceException("请选择需要转结算的明细");
|
||||
}
|
||||
if (!List.of("pre", "formal").contains(request.getSettlementBillType())) {
|
||||
throw new ServiceException("转结算类型不正确");
|
||||
}
|
||||
List<ReceivablePayableDetail> details = listByIds(request.getIds());
|
||||
if (details.size() != request.getIds().size()) {
|
||||
throw new ServiceException("存在无效的费用明细");
|
||||
}
|
||||
String billNo = settlementBillNo(request.getSettlementBillType());
|
||||
for (ReceivablePayableDetail detail : details) {
|
||||
if (!"pending".equals(detail.getSettlementStatus())) {
|
||||
throw new ServiceException("仅待结算明细允许转结算");
|
||||
}
|
||||
if ("pre".equals(request.getSettlementBillType())) {
|
||||
detail.setPreSettlementNo(billNo);
|
||||
detail.setSettlementStatus("pre_settled");
|
||||
} else {
|
||||
detail.setFormalSettlementNo(billNo);
|
||||
detail.setSettlementStatus("formal_settled");
|
||||
}
|
||||
updateById(detail);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public IPage<Map<String, Object>> transferCandidates(IPage<?> page, String contractName, String batchNo,
|
||||
String generateStartDate, String generateEndDate, String settlementBillType) {
|
||||
ReceivablePayableDetailVO query = new ReceivablePayableDetailVO();
|
||||
query.setContractName(contractName);
|
||||
query.setBatchNo(batchNo);
|
||||
query.setSettlementStatus("pending");
|
||||
query.setGenerateStartDate(parseDate(generateStartDate));
|
||||
query.setGenerateEndDate(parseDate(generateEndDate));
|
||||
IPage<ReceivablePayableDetailVO> detailPage = selectPage(new Page<>(page.getCurrent(), page.getSize()), query);
|
||||
Page<Map<String, Object>> result = new Page<>(detailPage.getCurrent(), detailPage.getSize(), detailPage.getTotal());
|
||||
result.setRecords(detailPage.getRecords().stream().map(this::beanMap).toList());
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public IPage<Map<String, Object>> generateWaybills(IPage<?> page, ReceivablePayableGenerateRequest request) {
|
||||
validateGenerateRequest(request, false);
|
||||
IPage<Waybill> waybillPage = waybillService.page(new Page<>(page.getCurrent(), page.getSize()), buildWaybillQuery(request));
|
||||
Page<Map<String, Object>> result = new Page<>(waybillPage.getCurrent(), waybillPage.getSize(), waybillPage.getTotal());
|
||||
result.setRecords(waybillPage.getRecords().stream().map(this::waybillMap).toList());
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ReceivablePayableFeeDetailVO generatePreview(IPage<?> page, ReceivablePayableGenerateRequest request) {
|
||||
validateGenerateRequest(request, true);
|
||||
List<Waybill> waybills = waybillService.list(buildWaybillQuery(request));
|
||||
List<ReceivablePayableCargoFee> fees = waybills.stream()
|
||||
.skip((page.getCurrent() - 1) * page.getSize())
|
||||
.limit(page.getSize())
|
||||
.map(waybill -> buildCargoFee(null, waybill))
|
||||
.toList();
|
||||
ReceivablePayableFeeDetailVO vo = buildFeeDetail(fees);
|
||||
vo.setTotal((long) waybills.size());
|
||||
return vo;
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void generateFee(ReceivablePayableGenerateRequest request) {
|
||||
validateGenerateRequest(request, true);
|
||||
List<Waybill> waybills = waybillService.list(buildWaybillQuery(request));
|
||||
if (Func.isEmpty(waybills)) {
|
||||
throw new ServiceException("没有可生成费用的运单");
|
||||
}
|
||||
ContractManage contract = contractManageService.getById(request.getContractId());
|
||||
for (Waybill waybill : waybills) {
|
||||
if (existsByWaybill(waybill.getId())) {
|
||||
continue;
|
||||
}
|
||||
ReceivablePayableDetail detail = buildDetail(waybill, contract);
|
||||
save(detail);
|
||||
ReceivablePayableCargoFee cargoFee = buildCargoFee(detail.getId(), waybill);
|
||||
cargoFeeMapper.insert(cargoFee);
|
||||
}
|
||||
}
|
||||
|
||||
private LambdaQueryWrapper<ReceivablePayableDetail> buildQuery(ReceivablePayableDetailVO query) {
|
||||
LambdaQueryWrapper<ReceivablePayableDetail> wrapper = Wrappers.<ReceivablePayableDetail>lambdaQuery()
|
||||
.eq(ReceivablePayableDetail::getIsDeleted, 0)
|
||||
.like(Func.isNotEmpty(query.getDocumentNo()), ReceivablePayableDetail::getDocumentNo, query.getDocumentNo())
|
||||
.ge(query.getGenerateStartDate() != null, ReceivablePayableDetail::getFeeDate, query.getGenerateStartDate())
|
||||
.le(query.getGenerateEndDate() != null, ReceivablePayableDetail::getFeeDate, query.getGenerateEndDate())
|
||||
.like(Func.isNotEmpty(query.getCustomerName()), ReceivablePayableDetail::getCustomerName, query.getCustomerName())
|
||||
.like(Func.isNotEmpty(query.getDeptName()), ReceivablePayableDetail::getDeptName, query.getDeptName())
|
||||
.like(Func.isNotEmpty(query.getProjectName()), ReceivablePayableDetail::getProjectName, query.getProjectName())
|
||||
.like(Func.isNotEmpty(query.getCargoType()), ReceivablePayableDetail::getCargoType, query.getCargoType())
|
||||
.like(Func.isNotEmpty(query.getCargoName()), ReceivablePayableDetail::getCargoName, query.getCargoName())
|
||||
.like(Func.isNotEmpty(query.getContractNo()), ReceivablePayableDetail::getContractNo, query.getContractNo())
|
||||
.like(Func.isNotEmpty(query.getContractName()), ReceivablePayableDetail::getContractName, query.getContractName())
|
||||
.like(Func.isNotEmpty(query.getPreSettlementNo()), ReceivablePayableDetail::getPreSettlementNo, query.getPreSettlementNo())
|
||||
.like(Func.isNotEmpty(query.getFormalSettlementNo()), ReceivablePayableDetail::getFormalSettlementNo, query.getFormalSettlementNo())
|
||||
.like(Func.isNotEmpty(query.getBatchNo()), ReceivablePayableDetail::getBatchNo, query.getBatchNo())
|
||||
.like(Func.isNotEmpty(query.getVehicleNo()), ReceivablePayableDetail::getVehicleNo, query.getVehicleNo())
|
||||
.eq(Func.isNotEmpty(query.getSettlementStatus()), ReceivablePayableDetail::getSettlementStatus, query.getSettlementStatus());
|
||||
return wrapper.orderByDesc(ReceivablePayableDetail::getCreateTime);
|
||||
}
|
||||
|
||||
private LambdaQueryWrapper<ReceivablePayableDetail> buildUpdateQuery(ReceivablePayableUpdateFeeRequest request) {
|
||||
LambdaQueryWrapper<ReceivablePayableDetail> wrapper = Wrappers.<ReceivablePayableDetail>lambdaQuery()
|
||||
.eq(ReceivablePayableDetail::getIsDeleted, 0)
|
||||
.eq(ReceivablePayableDetail::getSettlementStatus, "pending");
|
||||
if (Func.isNotEmpty(request.getIds())) {
|
||||
wrapper.in(ReceivablePayableDetail::getId, request.getIds());
|
||||
}
|
||||
if (Func.isNotEmpty(request.getContractId())) {
|
||||
wrapper.eq(ReceivablePayableDetail::getContractId, request.getContractId());
|
||||
}
|
||||
return wrapper;
|
||||
}
|
||||
|
||||
private LambdaQueryWrapper<Waybill> buildWaybillQuery(ReceivablePayableGenerateRequest request) {
|
||||
LambdaQueryWrapper<Waybill> wrapper = Wrappers.<Waybill>lambdaQuery()
|
||||
.eq(Waybill::getIsDeleted, 0)
|
||||
.eq(Waybill::getContractId, request.getContractId())
|
||||
.eq(Waybill::getBusinessStatus, "completed")
|
||||
.notInSql(Waybill::getId, "select waybill_id from blade_receivable_payable_detail where is_deleted = 0");
|
||||
if (Func.isNotEmpty(request.getBatchNo())) {
|
||||
wrapper.like(Waybill::getBatchNo, request.getBatchNo());
|
||||
}
|
||||
if (request.getFinishStartDate() != null) {
|
||||
wrapper.ge(Waybill::getEndDate, request.getFinishStartDate());
|
||||
}
|
||||
if (request.getFinishEndDate() != null) {
|
||||
wrapper.le(Waybill::getEndDate, request.getFinishEndDate());
|
||||
}
|
||||
if (Func.isNotEmpty(request.getWaybillIds())) {
|
||||
wrapper.in(Waybill::getId, request.getWaybillIds());
|
||||
}
|
||||
return wrapper.orderByDesc(Waybill::getCreateTime);
|
||||
}
|
||||
|
||||
private ReceivablePayableDetail buildDetail(Waybill waybill, ContractManage contract) {
|
||||
ReceivablePayableCargoFee cargoFee = buildCargoFee(null, waybill);
|
||||
ReceivablePayableDetail detail = new ReceivablePayableDetail();
|
||||
detail.setDocumentNo(nextDocumentNo());
|
||||
detail.setSettlementType("receivable");
|
||||
detail.setProjectId(waybill.getProjectId());
|
||||
detail.setProjectName(waybill.getProjectName());
|
||||
detail.setDeptId(waybill.getDeptId());
|
||||
detail.setDeptName(waybill.getDeptName());
|
||||
detail.setFeeDate(waybill.getEndDate() == null ? LocalDate.now() : waybill.getEndDate());
|
||||
detail.setCustomerName(waybill.getCustomerName());
|
||||
detail.setContractId(waybill.getContractId());
|
||||
detail.setContractNo(contract == null ? null : contract.getContractNo());
|
||||
detail.setContractName(waybill.getContractName());
|
||||
detail.setSourceType("系统生成");
|
||||
detail.setWaybillId(waybill.getId());
|
||||
detail.setWaybillNo(waybill.getWaybillNo());
|
||||
detail.setVehicleNo(waybill.getVehicleNo());
|
||||
detail.setTransportType(waybill.getTransportType());
|
||||
detail.setCargoName(waybill.getCargoName());
|
||||
detail.setCargoType(waybill.getCargoType());
|
||||
detail.setTransportQuantity(waybill.getQuantity());
|
||||
detail.setQuantityUnit(waybill.getQuantityUnit());
|
||||
detail.setMileage(waybill.getMileage());
|
||||
detail.setBatchNo(waybill.getBatchNo());
|
||||
detail.setUnitPrice(waybill.getUnitPrice());
|
||||
detail.setCurrency("RMB");
|
||||
detail.setFreightAmount(cargoFee.getFreightAmount());
|
||||
detail.setOtherFeeAmount(waybill.getOtherFeeTotal());
|
||||
detail.setTotalAmount(cargoFee.getAfterAmount());
|
||||
detail.setSettlementStatus("pending");
|
||||
detail.setFeeItemsJson(cargoFee.getFeeItemsJson());
|
||||
return detail;
|
||||
}
|
||||
|
||||
private ReceivablePayableCargoFee buildCargoFee(Long detailId, Waybill waybill) {
|
||||
BigDecimal quantity = money(waybill.getQuantity());
|
||||
BigDecimal unitPrice = money(waybill.getUnitPrice());
|
||||
BigDecimal freightAmount = quantity.multiply(unitPrice).setScale(2, RoundingMode.HALF_UP);
|
||||
BigDecimal otherFeeAmount = money(waybill.getOtherFeeTotal());
|
||||
Map<String, Object> feeItems = parseMap(waybill.getFreightJson());
|
||||
if (feeItems.isEmpty() && otherFeeAmount.compareTo(BigDecimal.ZERO) > 0) {
|
||||
feeItems.put("其它费用", otherFeeAmount);
|
||||
}
|
||||
BigDecimal feeItemTotal = feeItems.values().stream().map(this::decimal).reduce(BigDecimal.ZERO, BigDecimal::add);
|
||||
BigDecimal total = freightAmount.add(feeItemTotal).setScale(2, RoundingMode.HALF_UP);
|
||||
ReceivablePayableCargoFee cargoFee = new ReceivablePayableCargoFee();
|
||||
cargoFee.setDetailId(detailId);
|
||||
cargoFee.setWaybillId(waybill.getId());
|
||||
cargoFee.setLineNo("0001");
|
||||
cargoFee.setCargoName(waybill.getCargoName());
|
||||
cargoFee.setCargoType(waybill.getCargoType());
|
||||
cargoFee.setSpecification(waybill.getSpecification());
|
||||
cargoFee.setModel(waybill.getModel());
|
||||
cargoFee.setBillingFactor("按重量");
|
||||
cargoFee.setBillingType("固定单价");
|
||||
cargoFee.setTransportQuantity(quantity);
|
||||
cargoFee.setQuantityUnit(waybill.getQuantityUnit());
|
||||
cargoFee.setPriceUnit(waybill.getPriceUnit());
|
||||
cargoFee.setUnitPrice(unitPrice);
|
||||
cargoFee.setMileage(waybill.getMileage());
|
||||
cargoFee.setFreightAmount(freightAmount);
|
||||
cargoFee.setFeeItemsJson(JsonUtil.toJson(feeItems));
|
||||
cargoFee.setOriginalAmount(total);
|
||||
cargoFee.setAdjustAmount(BigDecimal.ZERO);
|
||||
cargoFee.setAfterAmount(total);
|
||||
cargoFee.setRemark(waybill.getRemark());
|
||||
return cargoFee;
|
||||
}
|
||||
|
||||
private ReceivablePayableFeeDetailVO buildFeeDetail(List<ReceivablePayableCargoFee> rows) {
|
||||
Set<String> feeItemNames = new LinkedHashSet<>();
|
||||
List<ReceivablePayableCargoFeeVO> records = rows.stream().map(row -> {
|
||||
ReceivablePayableCargoFeeVO vo = Objects.requireNonNull(BeanUtil.copyProperties(row, ReceivablePayableCargoFeeVO.class));
|
||||
Map<String, Object> feeItems = parseMap(row.getFeeItemsJson());
|
||||
feeItemNames.addAll(feeItems.keySet());
|
||||
vo.setFeeItems(feeItems);
|
||||
vo.setTransportQuantityText(formatQuantity(row.getTransportQuantity(), row.getQuantityUnit()));
|
||||
vo.setOriginalAmountText(formatMoney(row.getOriginalAmount()));
|
||||
vo.setAdjustAmountText(formatMoney(row.getAdjustAmount()));
|
||||
vo.setAfterAmountText(formatMoney(row.getAfterAmount()));
|
||||
vo.setUpdateUserName(UserCache.getUserRealName(row.getUpdateUser()));
|
||||
return vo;
|
||||
}).toList();
|
||||
ReceivablePayableFeeDetailVO vo = new ReceivablePayableFeeDetailVO();
|
||||
vo.setFeeItemNames(new ArrayList<>(feeItemNames));
|
||||
vo.setRecords(records);
|
||||
vo.setTotal((long) records.size());
|
||||
return vo;
|
||||
}
|
||||
|
||||
private void rebuildDetailFee(ReceivablePayableDetail detail) {
|
||||
Waybill waybill = waybillService.getById(detail.getWaybillId());
|
||||
if (waybill == null) {
|
||||
throw new ServiceException("关联运单不存在");
|
||||
}
|
||||
ReceivablePayableCargoFee cargoFee = buildCargoFee(detail.getId(), waybill);
|
||||
cargoFeeMapper.delete(Wrappers.<ReceivablePayableCargoFee>lambdaQuery().eq(ReceivablePayableCargoFee::getDetailId, detail.getId()));
|
||||
cargoFeeMapper.insert(cargoFee);
|
||||
detail.setFreightAmount(cargoFee.getFreightAmount());
|
||||
detail.setOtherFeeAmount(money(waybill.getOtherFeeTotal()));
|
||||
detail.setTotalAmount(cargoFee.getAfterAmount());
|
||||
detail.setFeeItemsJson(cargoFee.getFeeItemsJson());
|
||||
updateById(detail);
|
||||
}
|
||||
|
||||
private void closeDetails(List<Long> ids) {
|
||||
if (Func.isEmpty(ids)) {
|
||||
throw new ServiceException("请选择需要关闭的明细");
|
||||
}
|
||||
for (ReceivablePayableDetail detail : listByIds(ids)) {
|
||||
if (!"pending".equals(detail.getSettlementStatus())) {
|
||||
throw new ServiceException("仅待结算明细允许关闭");
|
||||
}
|
||||
detail.setSettlementStatus("closed");
|
||||
updateById(detail);
|
||||
}
|
||||
}
|
||||
|
||||
private void saveChangeRecord(ReceivablePayableDetail detail, String content, String reason) {
|
||||
ReceivablePayableChangeRecord record = new ReceivablePayableChangeRecord();
|
||||
record.setDetailId(detail.getId());
|
||||
record.setLineNo("0001");
|
||||
record.setCargoName(detail.getCargoName());
|
||||
record.setChangeContent(content);
|
||||
record.setAdjustUser(AuthUtil.getUserId());
|
||||
record.setAdjustUserName(AuthUtil.getUserName());
|
||||
record.setAdjustReason(reason);
|
||||
record.setAdjustTime(LocalDateTime.now());
|
||||
changeRecordMapper.insert(record);
|
||||
}
|
||||
|
||||
private ReceivablePayableDetail getExisting(Long id) {
|
||||
ReceivablePayableDetail detail = getById(id);
|
||||
if (detail == null || Objects.equals(detail.getIsDeleted(), 1)) {
|
||||
throw new ServiceException("应收应付明细不存在");
|
||||
}
|
||||
return detail;
|
||||
}
|
||||
|
||||
private boolean existsByWaybill(Long waybillId) {
|
||||
return count(Wrappers.<ReceivablePayableDetail>lambdaQuery()
|
||||
.eq(ReceivablePayableDetail::getWaybillId, waybillId)
|
||||
.eq(ReceivablePayableDetail::getIsDeleted, 0)) > 0;
|
||||
}
|
||||
|
||||
private void validateGenerateRequest(ReceivablePayableGenerateRequest request, boolean requireWaybill) {
|
||||
if (Func.isEmpty(request.getContractId())) {
|
||||
throw new ServiceException("请选择运单合同");
|
||||
}
|
||||
if (Func.isEmpty(request.getBillingPlanId())) {
|
||||
throw new ServiceException("请选择计费方案");
|
||||
}
|
||||
if (requireWaybill && Func.isEmpty(request.getWaybillIds())) {
|
||||
throw new ServiceException("请选择需要生成费用的运单");
|
||||
}
|
||||
}
|
||||
|
||||
private Map<String, Object> waybillMap(Waybill waybill) {
|
||||
Map<String, Object> map = new LinkedHashMap<>();
|
||||
map.put("id", waybill.getId());
|
||||
map.put("waybillNo", waybill.getWaybillNo());
|
||||
map.put("projectName", waybill.getProjectName());
|
||||
map.put("customerName", waybill.getCustomerName());
|
||||
map.put("vehicleNo", waybill.getVehicleNo());
|
||||
map.put("driverName", waybill.getDriverName());
|
||||
map.put("carrierName", waybill.getCarrierName());
|
||||
map.put("transportType", waybill.getTransportType());
|
||||
map.put("carrierType", waybill.getCarrierType());
|
||||
map.put("cargoInfo", waybill.getCargoName());
|
||||
return map;
|
||||
}
|
||||
|
||||
private Map<String, Object> beanMap(ReceivablePayableDetailVO detail) {
|
||||
Map<String, Object> map = new LinkedHashMap<>();
|
||||
BeanUtil.copyProperties(detail, map);
|
||||
return map;
|
||||
}
|
||||
|
||||
private Map<String, Object> parseMap(String json) {
|
||||
if (Func.isEmpty(json)) {
|
||||
return new LinkedHashMap<>();
|
||||
}
|
||||
try {
|
||||
Object parsed = JsonUtil.parse(json, Map.class);
|
||||
if (parsed instanceof Map<?, ?> source) {
|
||||
Map<String, Object> map = new LinkedHashMap<>();
|
||||
source.forEach((key, value) -> map.put(String.valueOf(key), value));
|
||||
return map;
|
||||
}
|
||||
if (parsed instanceof List<?> list && !list.isEmpty() && list.get(0) instanceof Map<?, ?> source) {
|
||||
Map<String, Object> map = new LinkedHashMap<>();
|
||||
source.forEach((key, value) -> {
|
||||
String name = String.valueOf(key);
|
||||
if (name.contains("费")) {
|
||||
map.put(name, value);
|
||||
}
|
||||
});
|
||||
return map;
|
||||
}
|
||||
} catch (Exception ignored) {
|
||||
return new LinkedHashMap<>();
|
||||
}
|
||||
return new LinkedHashMap<>();
|
||||
}
|
||||
|
||||
private BigDecimal decimal(Object value) {
|
||||
if (value == null || "".equals(value)) {
|
||||
return BigDecimal.ZERO;
|
||||
}
|
||||
try {
|
||||
return new BigDecimal(String.valueOf(value)).setScale(2, RoundingMode.HALF_UP);
|
||||
} catch (Exception ignored) {
|
||||
return BigDecimal.ZERO;
|
||||
}
|
||||
}
|
||||
|
||||
private BigDecimal money(BigDecimal value) {
|
||||
return value == null ? BigDecimal.ZERO : value.setScale(2, RoundingMode.HALF_UP);
|
||||
}
|
||||
|
||||
private String formatMoney(BigDecimal value) {
|
||||
return money(value).toPlainString();
|
||||
}
|
||||
|
||||
private String formatQuantity(BigDecimal quantity, String unit) {
|
||||
return money(quantity).stripTrailingZeros().toPlainString() + (unit == null ? "" : " " + unit);
|
||||
}
|
||||
|
||||
private LocalDate parseDate(String value) {
|
||||
return Func.isEmpty(value) ? null : LocalDate.parse(value);
|
||||
}
|
||||
|
||||
private synchronized String nextDocumentNo() {
|
||||
return "YS" + LocalDate.now().format(DateTimeFormatter.BASIC_ISO_DATE) + System.currentTimeMillis() % 100000;
|
||||
}
|
||||
|
||||
private synchronized String settlementBillNo(String type) {
|
||||
String prefix = "pre".equals(type) ? "YJ" : "ZJ";
|
||||
return prefix + LocalDate.now().format(DateTimeFormatter.BASIC_ISO_DATE) + System.currentTimeMillis() % 100000;
|
||||
}
|
||||
}
|
||||
+135
@@ -0,0 +1,135 @@
|
||||
package org.springblade.transport.service.impl;
|
||||
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.core.metadata.IPage;
|
||||
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
|
||||
import org.springblade.core.log.exception.ServiceException;
|
||||
import org.springblade.core.mp.base.BaseServiceImpl;
|
||||
import org.springblade.core.secure.utils.AuthUtil;
|
||||
import org.springblade.core.tool.utils.BeanUtil;
|
||||
import org.springblade.core.tool.utils.Func;
|
||||
import org.springblade.system.cache.UserCache;
|
||||
import org.springblade.transport.mapper.RiskDisposalMapper;
|
||||
import org.springblade.transport.pojo.dto.RiskDisposalBatchDisposeRequest;
|
||||
import org.springblade.transport.pojo.dto.RiskDisposalDisposeRequest;
|
||||
import org.springblade.transport.pojo.entity.RiskDisposal;
|
||||
import org.springblade.transport.pojo.vo.RiskDisposalBatchResultVO;
|
||||
import org.springblade.transport.pojo.vo.RiskDisposalVO;
|
||||
import org.springblade.transport.service.IRiskDisposalService;
|
||||
import org.springblade.transport.support.TransportBusinessSupport;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
import java.time.LocalDateTime;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
|
||||
@Service
|
||||
public class RiskDisposalServiceImpl extends BaseServiceImpl<RiskDisposalMapper, RiskDisposal> implements IRiskDisposalService {
|
||||
|
||||
private static final String STATUS_PENDING = "pending";
|
||||
private static final String STATUS_PROCESSED = "processed";
|
||||
private static final String STATUS_IGNORED = "ignored";
|
||||
|
||||
@Override
|
||||
public IPage<RiskDisposalVO> selectPage(IPage<RiskDisposal> page, RiskDisposalVO query) {
|
||||
IPage<RiskDisposal> entityPage = page(page, buildQuery(query));
|
||||
IPage<RiskDisposalVO> voPage = entityPage.convert(this::toVO);
|
||||
return voPage;
|
||||
}
|
||||
|
||||
@Override
|
||||
public RiskDisposalVO detail(Long id) {
|
||||
return toVO(getExisting(id));
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void dispose(RiskDisposalDisposeRequest request) {
|
||||
RiskDisposal risk = getExisting(request.getId());
|
||||
if (!STATUS_PENDING.equals(risk.getDisposalStatus())) {
|
||||
throw new ServiceException("仅待处理风险允许处置");
|
||||
}
|
||||
risk.setDisposalMethod(request.getDisposalMethod());
|
||||
risk.setDisposalRemark(TransportBusinessSupport.trimToNull(request.getDisposalRemark()));
|
||||
risk.setDisposalStatus("ignore".equals(request.getDisposalMethod()) ? STATUS_IGNORED : STATUS_PROCESSED);
|
||||
risk.setDisposeTime(LocalDateTime.now());
|
||||
updateById(risk);
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public RiskDisposalBatchResultVO batchDispose(RiskDisposalBatchDisposeRequest request) {
|
||||
RiskDisposalBatchResultVO result = new RiskDisposalBatchResultVO();
|
||||
if (request == null || Func.isEmpty(request.getIds())) {
|
||||
throw new ServiceException("请选择需要处理的风险");
|
||||
}
|
||||
for (Long id : request.getIds()) {
|
||||
try {
|
||||
dispose(single(id, request.getDisposalMethod(), request.getDisposalRemark()));
|
||||
result.setSuccessCount(result.getSuccessCount() + 1);
|
||||
} catch (Exception ex) {
|
||||
result.setSkippedCount(result.getSkippedCount() + 1);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
private RiskDisposalDisposeRequest single(Long id, String method, String remark) {
|
||||
RiskDisposalDisposeRequest request = new RiskDisposalDisposeRequest();
|
||||
request.setId(id);
|
||||
request.setDisposalMethod(method);
|
||||
request.setDisposalRemark(remark);
|
||||
return request;
|
||||
}
|
||||
|
||||
private LambdaQueryWrapper<RiskDisposal> buildQuery(RiskDisposalVO query) {
|
||||
return Wrappers.<RiskDisposal>lambdaQuery()
|
||||
.eq(RiskDisposal::getIsDeleted, 0)
|
||||
.like(Func.isNotEmpty(query.getRiskNo()), RiskDisposal::getRiskNo, query.getRiskNo())
|
||||
.like(Func.isNotEmpty(query.getRuleName()), RiskDisposal::getRuleName, query.getRuleName())
|
||||
.like(Func.isNotEmpty(query.getWaybillNo()), RiskDisposal::getWaybillNo, query.getWaybillNo())
|
||||
.like(Func.isNotEmpty(query.getProjectName()), RiskDisposal::getProjectName, query.getProjectName())
|
||||
.eq(Func.isNotEmpty(query.getRiskLevel()), RiskDisposal::getRiskLevel, query.getRiskLevel())
|
||||
.eq(Func.isNotEmpty(query.getDisposalStatus()), RiskDisposal::getDisposalStatus, query.getDisposalStatus())
|
||||
.orderByDesc(RiskDisposal::getCreateTime);
|
||||
}
|
||||
|
||||
private RiskDisposalVO toVO(RiskDisposal entity) {
|
||||
RiskDisposalVO vo = Objects.requireNonNull(BeanUtil.copyProperties(entity, RiskDisposalVO.class));
|
||||
vo.setCreateUserName(UserCache.getUserRealName(entity.getCreateUser()));
|
||||
vo.setUpdateUserName(UserCache.getUserRealName(entity.getUpdateUser()));
|
||||
vo.setRiskLevelName(levelName(entity.getRiskLevel()));
|
||||
vo.setDisposalStatusName(statusName(entity.getDisposalStatus()));
|
||||
return vo;
|
||||
}
|
||||
|
||||
private RiskDisposal getExisting(Long id) {
|
||||
if (id == null) {
|
||||
throw new ServiceException("风险记录不存在");
|
||||
}
|
||||
RiskDisposal risk = getById(id);
|
||||
if (risk == null || Objects.equals(risk.getIsDeleted(), 1)) {
|
||||
throw new ServiceException("风险记录不存在");
|
||||
}
|
||||
return risk;
|
||||
}
|
||||
|
||||
private String levelName(String level) {
|
||||
return switch (Func.toStr(level)) {
|
||||
case "low" -> "低";
|
||||
case "medium" -> "中";
|
||||
case "high" -> "高";
|
||||
default -> "";
|
||||
};
|
||||
}
|
||||
|
||||
private String statusName(String status) {
|
||||
return switch (Func.toStr(status)) {
|
||||
case STATUS_PENDING -> "待处理";
|
||||
case STATUS_PROCESSED -> "已处理";
|
||||
case STATUS_IGNORED -> "已忽略";
|
||||
default -> "";
|
||||
};
|
||||
}
|
||||
}
|
||||
+61
@@ -36,9 +36,12 @@ import org.springblade.transport.excel.WaybillExcel;
|
||||
import java.time.LocalDate;
|
||||
import java.time.format.DateTimeFormatter;
|
||||
import org.springblade.transport.mapper.WaybillMapper;
|
||||
import org.springblade.transport.pojo.entity.LoadingManage;
|
||||
import org.springblade.transport.pojo.entity.Waybill;
|
||||
import org.springblade.transport.pojo.vo.BusinessRemoveResultVO;
|
||||
import org.springblade.transport.pojo.vo.LoadingManageVO;
|
||||
import org.springblade.transport.pojo.vo.WaybillVO;
|
||||
import org.springblade.transport.service.ILoadingManageService;
|
||||
import org.springblade.transport.service.IWaybillService;
|
||||
import org.springblade.transport.support.TransportBusinessSupport;
|
||||
import org.springblade.transport.wrapper.WaybillWrapper;
|
||||
@@ -51,6 +54,7 @@ import java.util.LinkedHashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
/**
|
||||
* 运单管理 服务实现类
|
||||
@@ -60,6 +64,11 @@ import java.util.Objects;
|
||||
@Service
|
||||
public class WaybillServiceImpl extends BaseServiceImpl<WaybillMapper, Waybill> implements IWaybillService {
|
||||
|
||||
private static final String STATUS_DRAFT = "draft";
|
||||
|
||||
@jakarta.annotation.Resource
|
||||
private ILoadingManageService loadingManageService;
|
||||
|
||||
@Override
|
||||
public IPage<WaybillVO> selectWaybillPage(IPage<Waybill> page, WaybillVO waybill) {
|
||||
IPage<Waybill> entityPage = page(page, buildQuery(waybill));
|
||||
@@ -279,6 +288,58 @@ public class WaybillServiceImpl extends BaseServiceImpl<WaybillMapper, Waybill>
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public LoadingManageVO roadLoading(String ids) {
|
||||
List<Long> idList = Func.toLongList(ids);
|
||||
if (Func.isEmpty(idList)) {
|
||||
throw new ServiceException("请选择待配载运单");
|
||||
}
|
||||
List<Waybill> waybills = listByIds(idList);
|
||||
if (waybills.size() != idList.size()) {
|
||||
throw new ServiceException("待配载运单不存在或已删除");
|
||||
}
|
||||
Waybill first = waybills.get(0);
|
||||
LoadingManage loadingManage = new LoadingManage();
|
||||
loadingManage.setWaybillIdsJson(JsonUtil.toJson(idList));
|
||||
loadingManage.setLoadingSubNos(waybills.stream()
|
||||
.map(Waybill::getWaybillNo)
|
||||
.filter(Func::isNotEmpty)
|
||||
.collect(Collectors.joining(",")));
|
||||
loadingManage.setProjectId(first.getProjectId());
|
||||
loadingManage.setProjectName(first.getProjectName());
|
||||
loadingManage.setCustomerName(first.getCustomerName());
|
||||
loadingManage.setTransportType(first.getTransportType());
|
||||
loadingManage.setCargoType(first.getCargoType());
|
||||
loadingManage.setCargoName(first.getCargoName());
|
||||
loadingManage.setVehicleNo(first.getVehicleNo());
|
||||
loadingManage.setTrailerVehicleNo(first.getTrailerVehicleNo());
|
||||
loadingManage.setDriverName(first.getDriverName());
|
||||
loadingManage.setDriverPhone(first.getDriverPhone());
|
||||
loadingManage.setEscortName(first.getEscortName());
|
||||
loadingManage.setEscortPhone(first.getEscortPhone());
|
||||
loadingManage.setCarrierType(first.getCarrierType());
|
||||
loadingManage.setCarrierName(first.getCarrierName());
|
||||
loadingManage.setDepartureAddress(first.getDepartureAddress());
|
||||
loadingManage.setArrivalAddress(first.getArrivalAddress());
|
||||
loadingManage.setOriginalNo(first.getOriginalNo());
|
||||
loadingManage.setDataSource(first.getDataSource());
|
||||
loadingManage.setStartDate(first.getStartDate());
|
||||
loadingManage.setEndDate(first.getEndDate());
|
||||
loadingManage.setPlanName(first.getPlanName());
|
||||
loadingManage.setBatchNo(first.getBatchNo());
|
||||
loadingManage.setCurrentProcessNode(first.getCurrentProcessNode());
|
||||
loadingManage.setMileage(first.getMileage());
|
||||
loadingManage.setEstimatedStartDate(first.getEstimatedStartTime());
|
||||
loadingManage.setEstimatedEndDate(first.getEstimatedEndTime());
|
||||
loadingManage.setTaskRemark(first.getTaskRemark());
|
||||
loadingManage.setGoodsJson(first.getGoodsJson());
|
||||
loadingManage.setTaskInfoJson(first.getTaskInfoJson());
|
||||
loadingManage.setBusinessStatus(STATUS_DRAFT);
|
||||
loadingManageService.saveDraft(loadingManage);
|
||||
return loadingManageService.detail(loadingManage.getId());
|
||||
}
|
||||
|
||||
private LambdaQueryWrapper<Waybill> buildQuery(WaybillVO waybill) {
|
||||
TransportBusinessSupport.validateAllDept(waybill.getAllDept(), "运单管理");
|
||||
LambdaQueryWrapper<Waybill> queryWrapper = Wrappers.<Waybill>lambdaQuery().eq(Waybill::getIsDeleted, 0);
|
||||
|
||||
+74
@@ -0,0 +1,74 @@
|
||||
/**
|
||||
* BladeX Commercial License Agreement
|
||||
* Copyright (c) 2018-2099, https://bladex.cn. All rights reserved.
|
||||
* <p>
|
||||
* Use of this software is governed by the Commercial License Agreement
|
||||
* obtained after purchasing a license from BladeX.
|
||||
* <p>
|
||||
* 1. This software is for development use only under a valid license
|
||||
* from BladeX.
|
||||
* <p>
|
||||
* 2. Redistribution of this software's source code to any third party
|
||||
* without a commercial license is strictly prohibited.
|
||||
* <p>
|
||||
* 3. Licensees may copyright their own code but cannot use segments
|
||||
* from this software for such purposes. Copyright of this software
|
||||
* remains with BladeX.
|
||||
* <p>
|
||||
* Using this software signifies agreement to this License, and the software
|
||||
* must not be used for illegal purposes.
|
||||
* <p>
|
||||
* Author: Chill Zhuang (bladejava@qq.com)
|
||||
*/
|
||||
package org.springblade.transport.wrapper;
|
||||
|
||||
import org.springblade.core.mp.support.BaseEntityWrapper;
|
||||
import org.springblade.core.tool.jackson.JsonUtil;
|
||||
import org.springblade.core.tool.utils.BeanUtil;
|
||||
import org.springblade.system.cache.UserCache;
|
||||
import org.springblade.transport.pojo.entity.ReceivablePayableDetail;
|
||||
import org.springblade.transport.pojo.vo.ReceivablePayableDetailVO;
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
|
||||
/**
|
||||
* 应收应付明细包装类
|
||||
*
|
||||
* @author Chill
|
||||
*/
|
||||
public class ReceivablePayableDetailWrapper
|
||||
extends BaseEntityWrapper<ReceivablePayableDetail, ReceivablePayableDetailVO> {
|
||||
|
||||
public static ReceivablePayableDetailWrapper build() {
|
||||
return new ReceivablePayableDetailWrapper();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ReceivablePayableDetailVO entityVO(ReceivablePayableDetail entity) {
|
||||
ReceivablePayableDetailVO vo = Objects.requireNonNull(
|
||||
BeanUtil.copyProperties(entity, ReceivablePayableDetailVO.class));
|
||||
vo.setCreateUserName(UserCache.getUserRealName(entity.getCreateUser()));
|
||||
vo.setUpdateUserName(UserCache.getUserRealName(entity.getUpdateUser()));
|
||||
vo.setSettlementStatusName(statusName(entity.getSettlementStatus()));
|
||||
try {
|
||||
Object parsed = JsonUtil.parse(entity.getFeeItemsJson(), Map.class);
|
||||
if (parsed instanceof Map<?, ?> map) {
|
||||
vo.setFeeItems((Map<String, Object>) map);
|
||||
}
|
||||
} catch (Exception ignored) {
|
||||
// 兼容历史脏数据,列表仍需正常展示。
|
||||
}
|
||||
return vo;
|
||||
}
|
||||
|
||||
private String statusName(String status) {
|
||||
return switch (status == null ? "" : status) {
|
||||
case "pending" -> "待结算";
|
||||
case "pre_settled" -> "已转预结算";
|
||||
case "formal_settled" -> "已转正式结算";
|
||||
case "closed" -> "已关闭";
|
||||
default -> status;
|
||||
};
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user