feat(system): 增加部门和借支相关功能

- 新增获取公司信息的接口和相关逻辑
- 增加借支类型字段和相关查询功能- 优化租赁客户查询,增加工厂信息展示
- 修复部分接口的权限控制问题
This commit is contained in:
furongxin 2025-03-31 10:10:38 +08:00
parent 4a406637ed
commit 870b9df2b7
56 changed files with 1099 additions and 57 deletions

View File

@ -113,4 +113,9 @@ public interface DeptApi {
@Operation(summary = "获取指定类型的部门列表")
@Parameter(name = "type", description = "部门类型", required = true)
CommonResult<List<DeptRespDTO>> getDeptListByType(@RequestParam("type") String type);
@GetMapping("/getCompanyByDept")
@Operation(summary = "获取指定类型的部门列表")
@Parameter(name = "deptId", description = "部门编号", required = true)
CommonResult<DeptRespDTO> getCompanyByDept(@RequestParam("deptId") Long deptId);
}

View File

@ -12,6 +12,12 @@ import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestParam;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertMap;
@FeignClient(name = ApiConstants.NAME) // TODO 芋艿fallbackFactory =
@Tag(name = "RPC 服务 - 假期")
public interface LoanApi {
@ -25,5 +31,24 @@ public interface LoanApi {
@GetMapping(PREFIX + "/getByUserId")
@Operation(summary = "获取借支记录")
@Parameter(name = "userId", description = "用户编号", required = true)
CommonResult<LoanDTO> getByUserId(@RequestParam("userId") Long userId);
@Parameter(name = "loanType", description = "借支类型", required = true)
CommonResult<LoanDTO> getByUserId(@RequestParam("userId") Long userId,
@RequestParam("loanType") Integer loanType);
@GetMapping(PREFIX + "/getListByUserId")
@Operation(summary = "获取借支记录")
@Parameter(name = "userIds", description = "用户编号", required = true)
@Parameter(name = "loanType", description = "借支类型", required = true)
CommonResult<List<LoanDTO>> getListByUserId(@RequestParam("userIds") Collection<Long> userId,
@RequestParam("loanType") Integer loanType);
@GetMapping(PREFIX + "/getListByMonth")
@Operation(summary = "获取员工截止当前月份的工资借支余额")
@Parameter(name = "userIds", description = "用户编号", required = true)
@Parameter(name = "month", description = "月份", required = true)
CommonResult<List<LoanDTO>> getListByMonth(@RequestParam("userIds") Collection<Long> userId,
@RequestParam("month") String month);
}

View File

@ -25,6 +25,9 @@ public class LoanDTO {
@Schema(description = "借支用户部门名称")
private String deptName;
@Schema(description = "借支类型 | 1工资 2费用")
private Integer loanType;
@Schema(description = "借支总额")
private BigDecimal amount;

View File

@ -282,6 +282,7 @@ public interface ErrorCodeConstants {
ErrorCode RENTAL_REFUND_AMOUNT_EXCESS = new ErrorCode(1_013_001_007, "退款金额不能大于收款金额!");
ErrorCode RENTAL_ITEMS_NOT_REFUND = new ErrorCode(1_013_001_008, "物品还未全部退还,不能全额退款!");
ErrorCode RENTAL_ORDER_CUSTOMER_EXISTS = new ErrorCode(1_013_001_009, "该客户已存在租赁订单!");
ErrorCode RENTAL_SALE_RECORD_NOT_EXISTS = new ErrorCode(1_013_001_010, "租赁转销售记录不存在!");
// ========== 项目管理相关 1-014-001-001 ==========
ErrorCode PROJECT_NOT_EXISTS = new ErrorCode(1_014_001_001, "项目不存在!");

View File

@ -159,4 +159,11 @@ public class DeptApiImpl implements DeptApi {
List<DeptDO> deptList = deptService.getDeptListByType(type);
return success(BeanUtils.toBean(deptList, DeptRespDTO.class));
}
@Override
@DataPermission(enable = false)
public CommonResult<DeptRespDTO> getCompanyByDept(Long deptId) {
DeptDO dept = deptService.getCompanyByDept(deptId);
return success(BeanUtils.toBean(dept, DeptRespDTO.class));
}
}

View File

@ -11,6 +11,9 @@ import org.springframework.web.bind.annotation.RestController;
import javax.annotation.Resource;
import java.util.Collection;
import java.util.List;
import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
@RestController // 提供 RESTful API 接口 Feign 调用
@ -28,8 +31,20 @@ public class LoanApiImpl implements LoanApi {
}
@Override
public CommonResult<LoanDTO> getByUserId(Long userId) {
LoanDO loanDO = loanService.getByUserId(userId);
public CommonResult<LoanDTO> getByUserId(Long userId, Integer loanType) {
LoanDO loanDO = loanService.getByUserId(userId, loanType);
return success(BeanUtils.toBean(loanDO, LoanDTO.class));
}
@Override
public CommonResult<List<LoanDTO>> getListByUserId(Collection<Long> userId, Integer loanType) {
List<LoanDO> loanDOList = loanService.getListByUserId(userId, loanType);
return success(BeanUtils.toBean(loanDOList, LoanDTO.class));
}
@Override
public CommonResult<List<LoanDTO>> getListByMonth(Collection<Long> userId, String month) {
List<LoanDO> loanDOList = loanService.getListByMonth(userId, month);
return success(BeanUtils.toBean(loanDOList, LoanDTO.class));
}
}

View File

@ -71,10 +71,11 @@ public class CustomerSettlementController {
}
@PutMapping("/update-confirm")
@Operation(summary = "确认结算信息")
@Operation(summary = "修改结算状态")
@PreAuthorize("@ss.hasPermission('system:customer-settlement:update')")
public CommonResult<Boolean> updateConfirm(@RequestParam("id") Long id) {
customerSettlementService.updateConfirm(id);
public CommonResult<Boolean> updateConfirm(@RequestParam("id") Long id,
@RequestParam("status") Integer status) {
customerSettlementService.updateConfirm(id, status);
return success(true);
}

View File

@ -35,11 +35,14 @@ public class CustomerSettlementRespVO {
@Schema(description = "收款明细")
private List<PaymentItem> paymentItem;
@Schema(description = "其他扣款明细")
private List<OtherDeductionsVO> otherDeductions;
@Schema(description = "备注")
private String notes;
@Schema(description = "结算状态 | 1已复核 2已确认")
private Integer status;
@Schema(description = "附件")
private List<UploadUserFile> url;
private List<UploadUserFile> fileItems;
@Schema(description = "创建人")
private String creator;
@ -51,7 +54,4 @@ public class CustomerSettlementRespVO {
@Schema(description = "创建时间", requiredMode = Schema.RequiredMode.REQUIRED)
@ExcelProperty("创建时间")
private LocalDateTime createTime;
@Schema(description = "是否确认")
private Integer isConfirm;
}

View File

@ -29,10 +29,13 @@ public class CustomerSettlementSaveReqVO {
@Schema(description = "收款明细")
private List<PaymentItem> paymentItem;
@Schema(description = "其他扣款明细")
private List<OtherDeductionsVO> otherDeductions;
@Schema(description = "备注")
private String notes;
@Schema(description = "结算状态 | 1已复核 2已确认")
private Integer status;
@Schema(description = "上传附件", requiredMode = Schema.RequiredMode.NOT_REQUIRED, example = "https://www.iocoder.cn")
private List<UploadUserFile> url;
private List<UploadUserFile> fileItems;
}

View File

@ -3,11 +3,15 @@ package cn.iocoder.yudao.module.system.controller.admin.customersettlement.vo;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.math.BigDecimal;
@Schema(description = "管理后台 - 其他扣款明细 Response VO")
@Data
public class OtherDeductionsVO {
@Schema(description = "扣款项")
private String key;
private String value;
@Schema(description = "扣款金额")
private BigDecimal value;
}

View File

@ -5,6 +5,7 @@ import lombok.Data;
import javax.validation.constraints.NotNull;
import java.math.BigDecimal;
import java.util.List;
@Schema(description = "管理后台 - 结算明细新增/修改 Request VO")
@Data
@ -23,8 +24,8 @@ public class SettlementItemVO {
@Schema(description = "应结算金额")
private BigDecimal shouldSettlementAmount;
@Schema(description = "扣款金额")
private BigDecimal deductionAmount;
@Schema(description = "扣款明细")
private List<OtherDeductionsVO> deductionItems;
@Schema(description = "结算金额")
private BigDecimal settlementAmount;

View File

@ -60,7 +60,7 @@ public class LoanController {
@Parameter(name = "staffId", description = "员工编号", required = true, example = "1024")
@PreAuthorize("@ss.hasPermission('system:loan:query')")
public CommonResult<LoanRespVO> getByStaffId(@RequestParam("id") Long id) {
LoanDO loan = loanService.getByUserId(id);
LoanDO loan = loanService.getByUserId(id, 1);
return success(BeanUtils.toBean(loan, LoanRespVO.class));
}

View File

@ -19,6 +19,9 @@ public class LoanRespVO {
@Schema(description = "借支用户编号")
private Long userId;
@Schema(description = "借支员工编号")
private Long staffId;
@Schema(description = "借支用户姓名")
private String userName;
@ -28,6 +31,9 @@ public class LoanRespVO {
@Schema(description = "借支用户部门名称")
private String deptName;
@Schema(description = "借支类型 | 1工资 2费用")
private Integer loanType;
@Schema(description = "借支总额")
private BigDecimal amount;

View File

@ -18,9 +18,12 @@ public class LoanSaveReqVO {
private Long userId;
@Schema(description = "借支用户部门编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "128")
@NotNull(message = "借支用户部门编号不能为空")
private Long deptId;
@Schema(description = "借支类型 | 1工资 2费用")
@NotNull(message = "借支类型不能为空")
private Integer loanType;
@Schema(description = "借支总额")
private BigDecimal amount;

View File

@ -1,11 +1,15 @@
package cn.iocoder.yudao.module.system.controller.admin.rental;
import cn.hutool.core.collection.CollUtil;
import cn.iocoder.yudao.framework.common.pojo.CommonResult;
import cn.iocoder.yudao.framework.common.pojo.PageParam;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
import cn.iocoder.yudao.framework.excel.core.util.ExcelUtils;
import cn.iocoder.yudao.framework.operatelog.core.annotations.OperateLog;
import cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils;
import cn.iocoder.yudao.module.smartfactory.api.factoryInfo.FactoryInfoApi;
import cn.iocoder.yudao.module.smartfactory.api.factoryInfo.dto.FactoryInfoDTO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.customer.RentalCustomerPageReqVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.customer.RentalCustomerRespVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.customer.RentalCustomerSaveReqVO;
@ -24,9 +28,15 @@ import javax.servlet.http.HttpServletResponse;
import javax.validation.Valid;
import java.io.IOException;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Set;
import java.util.stream.Collectors;
import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertSet;
import static cn.iocoder.yudao.framework.operatelog.core.enums.OperateTypeEnum.EXPORT;
import static cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils.getLoginUserId;
@Tag(name = "管理后台 - 租赁客户")
@ -38,6 +48,9 @@ public class RentalCustomerController {
@Resource
private RentalCustomerService rentalCustomerService;
@Resource
private FactoryInfoApi factoryInfoApi;
@PostMapping("/create")
@Operation(summary = "创建租赁客户")
@PreAuthorize("@ss.hasPermission('system:rental-customer:create')")
@ -87,11 +100,47 @@ public class RentalCustomerController {
return success(BeanUtils.toBean(rentalCustomer, RentalCustomerRespVO.class));
}
@GetMapping("/get-list-by-factory")
@Operation(summary = "获得对应工厂的客户列表")
@Parameter(name = "userId", description = "用户id", required = true)
@PreAuthorize("@ss.hasPermission('system:rental-customer:query')")
public CommonResult<List<RentalCustomerRespVO>> getListByFactory(@RequestParam("userId") Long userId) {
List<RentalCustomerDO> rentalCustomer = rentalCustomerService.getListByFactory(userId);
return success(BeanUtils.toBean(rentalCustomer, RentalCustomerRespVO.class));
}
@GetMapping("/page")
@Operation(summary = "获得租赁客户分页")
@PreAuthorize("@ss.hasPermission('system:rental-customer:query')")
public CommonResult<PageResult<RentalCustomerRespVO>> getRentalCustomerPage(@Valid RentalCustomerPageReqVO pageReqVO) {
PageResult<RentalCustomerDO> pageResult = rentalCustomerService.getRentalCustomerPage(pageReqVO);
return success(BeanUtils.toBean(pageResult, RentalCustomerRespVO.class));
PageResult<RentalCustomerRespVO> respVO = BeanUtils.toBean(pageResult, RentalCustomerRespVO.class);
if (CollUtil.isNotEmpty(respVO.getList())) {
// 获取工厂编号
Set<Long> factoryIds = pageResult.getList().stream()
.map(RentalCustomerDO::getFactoryIds)
.filter(Objects::nonNull)
.flatMap(Set::stream)
.collect(Collectors.toSet());
// 获取工厂信息
List<FactoryInfoDTO> factoryInfoDTOS = factoryInfoApi.getFactoryInfoList(factoryIds).getCheckedData();
// 映射工厂名称
Map<Long, String> factoryMap = factoryInfoDTOS.stream()
.collect(Collectors.toMap(FactoryInfoDTO::getId, FactoryInfoDTO::getShortName));
respVO.getList().forEach(item -> {
// 设置工厂名称
Set<Long> itemFactoryIds = item.getFactoryIds();
if (itemFactoryIds != null) {
List<String> factoryNames = itemFactoryIds.stream()
.map(factoryMap::get)
.filter(Objects::nonNull)
.collect(Collectors.toList());
item.setFactoryNames(factoryNames);
}
});
}
return success(respVO);
}
}

View File

@ -1,5 +1,6 @@
package cn.iocoder.yudao.module.system.controller.admin.rental;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.collection.CollectionUtil;
import cn.iocoder.yudao.framework.common.pojo.CommonResult;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
@ -31,6 +32,8 @@ import java.util.Objects;
import java.util.stream.Collectors;
import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertList;
import static cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils.getLoginUserId;
@Tag(name = "管理后台 - 租赁订单")
@ -101,10 +104,33 @@ public class RentalOrderController {
return success(respVO);
}
@GetMapping("/getByOrderNo")
@Operation(summary = "获得租赁订单")
@Parameter(name = "orderNo", description = "订单编号", required = true, example = "1024")
@PreAuthorize("@ss.hasPermission('system:rental-order:query')")
public CommonResult<RentalOrderRespVO> getRentalOrder(@RequestParam("orderNo") String orderNo) {
RentalOrderDO rentalOrder = rentalOrderService.getRentalOrder(orderNo);
RentalOrderRespVO respVO = BeanUtils.toBean(rentalOrder, RentalOrderRespVO.class);
// 获取已收金额
RentalDepositAmountReqVO amountReqVO = rentalDepositRecordService.getRentalDepositRecordAmount(rentalOrder.getOrderNo(), false);
// 设置剩余金额 = 已收金额 - 已退金额
respVO.setRemainingDeposit(amountReqVO.getReceivedAmount().subtract(amountReqVO.getRefundAmount()));
return success(respVO);
}
@GetMapping("/page")
@Operation(summary = "获得租赁订单分页")
@PreAuthorize("@ss.hasPermission('system:rental-order:query')")
public CommonResult<PageResult<RentalOrderRespVO>> getRentalOrderPage(@Valid RentalOrderPageReqVO pageReqVO) {
// 获取当前登陆用户的 所属工厂的客户信息
List<RentalCustomerDO> rentalCustomerDOList = rentalCustomerService.getListByFactory(getLoginUserId());
if (CollUtil.isNotEmpty(rentalCustomerDOList)) {
pageReqVO.setCustomerIds(convertList(rentalCustomerDOList, RentalCustomerDO::getId));
}
PageResult<RentalOrderRespVO> pageResult = rentalOrderService.getRentalOrderPage(pageReqVO);
// 获取等待退款的订单号
List<String> orderNos = pageResult.getList().stream()
@ -118,7 +144,6 @@ public class RentalOrderController {
// 设置对应的订单号中的 申请退款和扣款金额
pageResult.getList().forEach(item -> {
// 设置剩余押金
item.setRemainingDeposit(item.getReceivedAmount().subtract(item.getRefundAmount().add(item.getChargebacksAmount())));

View File

@ -0,0 +1,96 @@
package cn.iocoder.yudao.module.system.controller.admin.rental;
import cn.hutool.core.collection.CollUtil;
import cn.iocoder.yudao.framework.common.pojo.CommonResult;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordPageReqVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordRespVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordSaveReqVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleStatusReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.rental.RentalSaleRecordDO;
import cn.iocoder.yudao.module.system.dal.dataobject.user.AdminUserDO;
import cn.iocoder.yudao.module.system.service.rental.RentalSaleRecordService;
import cn.iocoder.yudao.module.system.service.user.AdminUserService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
import javax.validation.Valid;
import java.util.List;
import java.util.Map;
import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertList;
import static cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils.getLoginUserId;
@Tag(name = "管理后台 - 租赁转销售记录")
@RestController
@RequestMapping("/system/rental-sale-record")
@Validated
public class RentalSaleRecordController {
@Resource
private RentalSaleRecordService rentalSaleRecordService;
@Resource
private AdminUserService userService;
@PostMapping("/create")
@Operation(summary = "创建租赁转销售记录")
public CommonResult<Long> createRentalSaleRecord(@Valid @RequestBody RentalSaleRecordSaveReqVO createReqVO) {
return success(rentalSaleRecordService.createRentalSaleRecord(createReqVO));
}
@PutMapping("/update")
@Operation(summary = "更新租赁转销售状态")
@PreAuthorize("@ss.hasPermission('system:rental-sale-record:update')")
public CommonResult<Boolean> updateRentalSaleRecord(@Valid @RequestBody RentalSaleStatusReqVO updateReqVO) {
if (updateReqVO.getStatus() == 1) {
updateReqVO.setReturnUserId(getLoginUserId());
}
rentalSaleRecordService.updateRentalSaleRecord(updateReqVO);
return success(true);
}
@DeleteMapping("/delete")
@Operation(summary = "删除租赁转销售记录")
@Parameter(name = "id", description = "编号", required = true)
public CommonResult<Boolean> deleteRentalSaleRecord(@RequestParam("id") Long id) {
rentalSaleRecordService.deleteRentalSaleRecord(id);
return success(true);
}
@GetMapping("/get")
@Operation(summary = "获得租赁转销售记录")
@Parameter(name = "id", description = "编号", required = true, example = "1024")
public CommonResult<RentalSaleRecordRespVO> getRentalSaleRecord(@RequestParam("id") Long id) {
RentalSaleRecordDO rentalSaleRecord = rentalSaleRecordService.getRentalSaleRecord(id);
return success(BeanUtils.toBean(rentalSaleRecord, RentalSaleRecordRespVO.class));
}
@GetMapping("/page")
@Operation(summary = "获得租赁转销售记录分页")
public CommonResult<PageResult<RentalSaleRecordRespVO>> getRentalSaleRecordPage(@Valid RentalSaleRecordPageReqVO pageReqVO) {
PageResult<RentalSaleRecordDO> pageResult = rentalSaleRecordService.getRentalSaleRecordPage(pageReqVO);
PageResult<RentalSaleRecordRespVO> respVO = BeanUtils.toBean(pageResult, RentalSaleRecordRespVO.class);
if (CollUtil.isNotEmpty(respVO.getList())) {
// 获取退还经办人信息
List<Long> userIds = convertList(respVO.getList(), RentalSaleRecordRespVO::getReturnUserId);
Map<Long, AdminUserDO> userMap = userService.getUserMap(userIds);
respVO.getList().forEach(item -> {
// 设置退还经办人名称
item.setReturnUserName(userMap.containsKey(item.getReturnUserId()) ? userMap.get(item.getReturnUserId()).getNickname() : "");
});
}
return success(respVO);
}
}

View File

@ -33,6 +33,9 @@ public class RentalCustomerPageReqVO extends PageParam {
@Schema(description = "剩余押金金额")
private BigDecimal amount;
@Schema(description = "工厂id")
private Long factoryId;
@Schema(description = "创建时间")
@DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND)
private LocalDateTime[] createTime;

View File

@ -5,6 +5,8 @@ import lombok.Data;
import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.List;
import java.util.Set;
@Schema(description = "管理后台 - 租赁客户 Response VO")
@Data
@ -13,6 +15,12 @@ public class RentalCustomerRespVO {
@Schema(description = "租赁客户表单主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
private Long id;
@Schema(description = "所属工厂id集合")
private Set<Long> factoryIds;
@Schema(description = "工厂名称")
private List<String> factoryNames;
@Schema(description = "客户名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "赵六")
private String name;
@ -31,6 +39,9 @@ public class RentalCustomerRespVO {
@Schema(description = "状态 | 0开启 1关闭")
private Integer status;
@Schema(description = "周转天数")
private Integer turnoverDays;
@Schema(description = "创建时间", requiredMode = Schema.RequiredMode.REQUIRED)
private LocalDateTime createTime;

View File

@ -4,7 +4,9 @@ import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import java.math.BigDecimal;
import java.util.Set;
@Schema(description = "管理后台 - 租赁客户新增/修改 Request VO")
@Data
@ -13,6 +15,9 @@ public class RentalCustomerSaveReqVO {
@Schema(description = "租赁客户表单主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
private Long id;
@Schema(description = "所属工厂id集合")
private Set<Long> factoryIds;
@Schema(description = "客户名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "赵六")
private String name;
@ -30,6 +35,10 @@ public class RentalCustomerSaveReqVO {
@Schema(description = "剩余押金金额")
private BigDecimal amount;
@Schema(description = "周转天数")
@NotNull(message = "周转天数不能为空")
private Integer turnoverDays;
@Schema(description = "状态 | 0开启 1关闭")
private Integer status;
}

View File

@ -8,6 +8,7 @@ import lombok.ToString;
import org.springframework.format.annotation.DateTimeFormat;
import java.time.LocalDateTime;
import java.util.List;
import static cn.iocoder.yudao.framework.common.util.date.DateUtils.FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND;
@ -26,6 +27,9 @@ public class RentalOrderPageReqVO extends PageParam {
@Schema(description = "客户编号")
private Long customerId;
@Schema(description = "客户编号")
private List<Long> customerIds;
@Schema(description = "押金金额")
private Integer depositAmount;

View File

@ -33,7 +33,7 @@ public class RentalDepositRecordSaveReqVO {
private String bankNo;
@Schema(description = "客户银行卡号", requiredMode = Schema.RequiredMode.REQUIRED)
@NotEmpty(message = "客户银行卡号不能为空")
@NotNull(message = "客户银行卡号不能为空")
private String customerBankNo;
@Schema(description = "收款/退款金额", requiredMode = Schema.RequiredMode.REQUIRED)

View File

@ -0,0 +1,39 @@
package cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord;
import cn.iocoder.yudao.framework.common.pojo.PageParam;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import lombok.EqualsAndHashCode;
import lombok.ToString;
import org.springframework.format.annotation.DateTimeFormat;
import java.math.BigDecimal;
import java.time.LocalDate;
import java.time.LocalDateTime;
import static cn.iocoder.yudao.framework.common.util.date.DateUtils.FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND;
@Schema(description = "管理后台 - 租赁转销售记录分页 Request VO")
@Data
@EqualsAndHashCode(callSuper = true)
@ToString(callSuper = true)
public class RentalSaleRecordPageReqVO extends PageParam {
@Schema(description = "订单编号", example = "1024")
private String orderNo;
@Schema(description = "转销售记录日期")
@DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND)
private LocalDate[] saleDate;
@Schema(description = "状态 | 0销售 1退还", example = "0")
private Integer status;
@Schema(description = "退还经办人用户编号", example = "146")
private Long returnUserId;
@Schema(description = "创建时间")
@DateTimeFormat(pattern = FORMAT_YEAR_MONTH_DAY_HOUR_MINUTE_SECOND)
private LocalDateTime[] createTime;
}

View File

@ -0,0 +1,47 @@
package cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord;
import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
import com.alibaba.excel.annotation.ExcelProperty;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import javax.validation.constraints.NotNull;
import java.math.BigDecimal;
import java.time.LocalDate;
import java.time.LocalDateTime;
@Schema(description = "管理后台 - 租赁转销售记录 Response VO")
@Data
public class RentalSaleRecordRespVO {
@Schema(description = "订单租赁物品记录表单主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
private Long id;
@Schema(description = "客户编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
private Long customerId;
@Schema(description = "订单编号", requiredMode = Schema.RequiredMode.REQUIRED)
private String orderNo;
@Schema(description = "入账记录表主键编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
private Long depositId;
@Schema(description = "金额", requiredMode = Schema.RequiredMode.REQUIRED)
private BigDecimal amount;
@Schema(description = "转销售记录日期", requiredMode = Schema.RequiredMode.REQUIRED)
private LocalDate saleDate;
@Schema(description = "状态 | 0销售 1退还", requiredMode = Schema.RequiredMode.REQUIRED, example = "0")
private Integer status;
@Schema(description = "退还经办人用户编号", example = "146")
private Long returnUserId;
@Schema(description = "退还经办人用户名称", example = "146")
private String returnUserName;
@Schema(description = "创建时间", requiredMode = Schema.RequiredMode.REQUIRED)
private LocalDateTime createTime;
}

View File

@ -0,0 +1,45 @@
package cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import java.math.BigDecimal;
import java.time.LocalDate;
@Schema(description = "管理后台 - 租赁转销售记录新增/修改 Request VO")
@Data
public class RentalSaleRecordSaveReqVO {
@Schema(description = "订单租赁物品记录表单主键", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
private Long id;
@Schema(description = "客户编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
@NotNull(message = "客户编号不能为空")
private Long customerId;
@Schema(description = "订单编号", requiredMode = Schema.RequiredMode.REQUIRED)
@NotEmpty(message = "订单编号不能为空")
private String orderNo;
@Schema(description = "入账记录表主键编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
@NotNull(message = "入账记录表主键编号不能为空")
private Long depositId;
@Schema(description = "金额", requiredMode = Schema.RequiredMode.REQUIRED)
@NotNull(message = "金额不能为空")
private BigDecimal amount;
@Schema(description = "转销售记录日期", requiredMode = Schema.RequiredMode.REQUIRED)
@NotNull(message = "转销售记录日期不能为空")
private LocalDate saleDate;
@Schema(description = "状态 | 0销售 1退还", requiredMode = Schema.RequiredMode.REQUIRED, example = "0")
@NotNull(message = "状态 | 0销售 1退还不能为空")
private Integer status;
@Schema(description = "退还经办人用户编号", example = "146")
private Long returnUserId;
}

View File

@ -0,0 +1,32 @@
package cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import javax.validation.constraints.NotNull;
import java.math.BigDecimal;
@Schema(description = "管理后台 - 租金转销售状态 Request VO")
@Data
public class RentalSaleStatusReqVO {
@Schema(description = "编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "1024")
@NotNull(message = "编号不能为空")
private Long id;
@Schema(description = "客户编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
private Long customerId;
@Schema(description = "入账编号")
private Long depositId;
@Schema(description = "金额")
private BigDecimal amount;
@Schema(description = "状态 | 0销售 1退还", requiredMode = Schema.RequiredMode.REQUIRED, example = "0")
@NotNull(message = "状态不能为空")
private Integer status;
@Schema(description = "退还经办人用户编号", example = "146")
private Long returnUserId;
}

View File

@ -50,19 +50,18 @@ public class CustomerSettlementDO extends BaseDO {
private List<PaymentItem> paymentItem;
/**
* 其他扣款明细
* 备注
*/
@TableField(typeHandler = JacksonTypeHandler.class)
private List<OtherDeductionsVO> otherDeductions;
private String notes;
/**
* 结算状态 | 1已复核 2已确认
*/
private Integer status;
/**
* 上传附件
*/
@TableField(typeHandler = JacksonTypeHandler.class)
private List<UploadUserFile> url;
/**
* 是否确认 | 0否 1是
*/
private Integer isConfirm;
private List<UploadUserFile> fileItems;
}

View File

@ -1,11 +1,15 @@
package cn.iocoder.yudao.module.system.dal.dataobject.customersettlement;
import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
import cn.iocoder.yudao.module.system.controller.admin.customersettlement.vo.OtherDeductionsVO;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import com.baomidou.mybatisplus.extension.handlers.JacksonTypeHandler;
import lombok.*;
import java.math.BigDecimal;
import java.util.List;
/**
* 结算明细信息 DO
@ -48,9 +52,10 @@ public class SettlementItemDO extends BaseDO {
private BigDecimal shouldSettlementAmount;
/**
* 扣款金额
* 扣款明细
*/
private BigDecimal deductionAmount;
@TableField(typeHandler = JacksonTypeHandler.class)
private List<OtherDeductionsVO> deductionItems;
/**
* 结算金额

View File

@ -36,6 +36,10 @@ public class LoanDO extends BaseDO {
* 借支用户部门编号
*/
private Long deptId;
/**
* 借支类型 | 1工资 2费用
*/
private Integer loanType;
/**
* 借支总额
*/

View File

@ -1,18 +1,22 @@
package cn.iocoder.yudao.module.system.dal.dataobject.rental;
import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
import cn.iocoder.yudao.framework.mybatis.core.type.JsonLongSetTypeHandler;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.*;
import java.math.BigDecimal;
import java.util.List;
import java.util.Set;
/**
* 租赁客户 DO
*
* @author 符溶馨
*/
@TableName("system_rental_customer")
@TableName(value = "system_rental_customer", autoResultMap = true)
@Data
@EqualsAndHashCode(callSuper = true)
@ToString(callSuper = true)
@ -26,6 +30,11 @@ public class RentalCustomerDO extends BaseDO {
*/
@TableId
private Long id;
/**
* 所属工厂集合
*/
@TableField(typeHandler = JsonLongSetTypeHandler.class)
private Set<Long> factoryIds;
/**
* 客户名称
*/
@ -47,6 +56,11 @@ public class RentalCustomerDO extends BaseDO {
*/
private BigDecimal amount;
/**
* 周转天数
*/
private Integer turnoverDays;
/**
* 状态 0开启 1关闭
*/

View File

@ -62,7 +62,7 @@ public class RentalDepositRecordDO extends BaseDO {
*/
private LocalDate paymentDate;
/**
* 类型 | 1收款 2退款
* 类型 | 1收款 2退款 3转销售
*/
private Integer type;
/**

View File

@ -0,0 +1,61 @@
package cn.iocoder.yudao.module.system.dal.dataobject.rental;
import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
import com.baomidou.mybatisplus.annotation.KeySequence;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.*;
import java.math.BigDecimal;
import java.time.LocalDate;
/**
* 租赁转销售记录 DO
*
* @author 符溶馨
*/
@TableName("system_rental_sale_record")
@KeySequence("system_rental_sale_record_seq") // 用于 OraclePostgreSQLKingbaseDB2H2 数据库的主键自增如果是 MySQL 等数据库可不写
@Data
@EqualsAndHashCode(callSuper = true)
@ToString(callSuper = true)
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class RentalSaleRecordDO extends BaseDO {
/**
* 订单租赁物品记录表单主键
*/
@TableId
private Long id;
/**
* 客户编号
*/
private Long customerId;
/**
* 订单编号
*/
private String orderNo;
/**
* 入账记录表主键编号
*/
private Long depositId;
/**
* 金额
*/
private BigDecimal amount;
/**
* 转销售记录日期
*/
private LocalDate saleDate;
/**
* 状态 | 0销售 1退还
*/
private Integer status;
/**
* 退还经办人用户编号
*/
private Long returnUserId;
}

View File

@ -6,6 +6,10 @@ import cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX;
import cn.iocoder.yudao.module.system.controller.admin.loan.vo.LoanPageReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.loan.LoanDO;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
import java.util.Collection;
import java.util.List;
/**
* 借支管理 Mapper
@ -20,7 +24,8 @@ public interface LoanMapper extends BaseMapperX<LoanDO> {
.eqIfPresent(LoanDO::getUserId, reqVO.getUserId())
.eqIfPresent(LoanDO::getDeptId, reqVO.getDeptId())
.betweenIfPresent(LoanDO::getCreateTime, reqVO.getCreateTime())
.orderByDesc(LoanDO::getId));
.orderByDesc(LoanDO::getUserId));
}
List<LoanDO> selectListByMonth(@Param("userId") Collection<Long> userId, @Param("month") String month);
}

View File

@ -6,6 +6,10 @@ import cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.customer.RentalCustomerPageReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.rental.RentalCustomerDO;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
import java.util.List;
import java.util.Objects;
/**
* 租赁客户 Mapper
@ -23,7 +27,9 @@ public interface RentalCustomerMapper extends BaseMapperX<RentalCustomerDO> {
.eqIfPresent(RentalCustomerDO::getBankNo, reqVO.getBankNo())
.eqIfPresent(RentalCustomerDO::getAmount, reqVO.getAmount())
.betweenIfPresent(RentalCustomerDO::getCreateTime, reqVO.getCreateTime())
.apply(Objects.nonNull(reqVO.getFactoryId()), "JSON_CONTAINS(factory_ids, '{0}', '$')", reqVO.getFactoryId())
.orderByDesc(RentalCustomerDO::getId));
}
List<RentalCustomerDO> selectListByFactory(@Param("userId") Long userId);
}

View File

@ -10,6 +10,7 @@ import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
import java.math.BigDecimal;
import java.util.List;
/**
* 租赁订单押金记录 Mapper

View File

@ -39,6 +39,7 @@ public interface RentalOrderMapper extends BaseMapperX<RentalOrderDO> {
.eqIfPresent(RentalOrderDO::getStatus, reqVO.getStatus())
.likeIfPresent(RentalOrderDO::getRecipient, reqVO.getRecipient())
.betweenIfPresent(RentalOrderDO::getCreateTime, reqVO.getCreateTime())
.inIfPresent(RentalOrderDO::getCustomerId, reqVO.getCustomerIds())
.groupBy(RentalOrderDO::getOrderNo)
.orderByDesc(RentalOrderDO::getCreateTime);

View File

@ -0,0 +1,32 @@
package cn.iocoder.yudao.module.system.dal.mysql.rental;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.mybatis.core.mapper.BaseMapperX;
import cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordPageReqVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordRespVO;
import cn.iocoder.yudao.module.system.dal.dataobject.rental.RentalSaleRecordDO;
import org.apache.ibatis.annotations.Mapper;
import java.util.List;
/**
* 租赁转销售记录 Mapper
*
* @author 符溶馨
*/
@Mapper
public interface RentalSaleRecordMapper extends BaseMapperX<RentalSaleRecordDO> {
default PageResult<RentalSaleRecordDO> selectPage(RentalSaleRecordPageReqVO reqVO) {
return selectPage(reqVO, new LambdaQueryWrapperX<RentalSaleRecordDO>()
.eqIfPresent(RentalSaleRecordDO::getOrderNo, reqVO.getOrderNo())
.betweenIfPresent(RentalSaleRecordDO::getSaleDate, reqVO.getSaleDate())
.eqIfPresent(RentalSaleRecordDO::getStatus, reqVO.getStatus())
.eqIfPresent(RentalSaleRecordDO::getReturnUserId, reqVO.getReturnUserId())
.betweenIfPresent(RentalSaleRecordDO::getCreateTime, reqVO.getCreateTime())
.orderByDesc(RentalSaleRecordDO::getId));
}
List<RentalSaleRecordRespVO> selectSaleDepositRecordList();
}

View File

@ -113,4 +113,11 @@ public interface RedisKeyConstants {
* VALUE 数据格式String 剩余金额
*/
String RENTAL_ORDER_AMOUNT = "rental_order_amount";
/**
* 所有公司类型部门的缓存
* KEY 格式company_dept
* VALUE 数据格式String 剩余金额
*/
String COMPANY_DEPT = "COMPANY_DEPT";
}

View File

@ -0,0 +1,83 @@
package cn.iocoder.yudao.module.system.job.rental;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
import cn.iocoder.yudao.framework.tenant.core.job.TenantJob;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordRespVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordSaveReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.rental.RentalCustomerDO;
import cn.iocoder.yudao.module.system.dal.dataobject.rental.RentalDepositRecordDO;
import cn.iocoder.yudao.module.system.dal.mysql.rental.RentalCustomerMapper;
import cn.iocoder.yudao.module.system.service.rental.RentalDepositRecordService;
import cn.iocoder.yudao.module.system.service.rental.RentalSaleRecordService;
import com.xxl.job.core.biz.model.ReturnT;
import com.xxl.job.core.handler.annotation.XxlJob;
import lombok.extern.slf4j.Slf4j;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.stereotype.Component;
import javax.annotation.Resource;
import java.math.BigDecimal;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
@Component
@Slf4j
@EnableScheduling
public class RentalSaleJob {
@Resource
private RentalSaleRecordService saleRecordService;
@Resource
private RentalCustomerMapper customerMapper;
@Resource
private RentalDepositRecordService depositRecordService;
@XxlJob("rentalSaleJob")
@TenantJob // --- 这个注解 会将租户列表拉出来 完了后逐个租户执行 定时任务需要注意
public ReturnT<String> execute() {
// 获取 当前日期已到达周转日期的收款记录
List<RentalSaleRecordRespVO> saleRecordList = saleRecordService.getSaleDepositRecordList();
List<RentalSaleRecordSaveReqVO> saleRecordSaveReqVOList = BeanUtils.toBean(saleRecordList, RentalSaleRecordSaveReqVO.class);
// 插入销售数据
saleRecordService.createBatch(saleRecordSaveReqVOList);
// 映射出一个map key为客户编号 value为 saleRecordSaveReqVOList该客户金额的和
Map<Long, BigDecimal> customerAmountMap = saleRecordSaveReqVOList.stream()
.collect(Collectors.groupingBy(
RentalSaleRecordSaveReqVO::getCustomerId,
Collectors.reducing(BigDecimal.ZERO, RentalSaleRecordSaveReqVO::getAmount, BigDecimal::add)
));
// 获取所有客户信息
List<RentalCustomerDO> RentalCustomerDO = customerMapper.selectList();
// 更新客户押金金额
RentalCustomerDO = RentalCustomerDO.stream()
.peek(customer -> {
BigDecimal originalAmount = customer.getAmount();
BigDecimal deductionAmount = customerAmountMap.getOrDefault(customer.getId(), BigDecimal.ZERO);
customer.setAmount(originalAmount.subtract(deductionAmount));
})
.collect(Collectors.toList());
// 同步更新 客户押金金额
customerMapper.updateBatch(RentalCustomerDO);
List<RentalDepositRecordDO> updateList = saleRecordList.stream()
.map(saleRecord -> new RentalDepositRecordDO()
.setId(saleRecord.getDepositId())
.setType(3))
.collect(Collectors.toList());
// 同步更新 租金记录表
depositRecordService.updateRentalDepositRecordType(updateList);
// 返回执行成功
return ReturnT.SUCCESS;
}
}

View File

@ -65,7 +65,9 @@ public interface CustomerSettlementService {
/**
* 更新结算信息确认状态
*
* @param id 编号
* @param status
*/
void updateConfirm(Long id);
void updateConfirm(Long id, Integer status);
}

View File

@ -63,7 +63,7 @@ public class CustomerSettlementServiceImpl implements CustomerSettlementService
settlementItemMapper.insertBatch(itemDO);
}
if (CollUtil.isNotEmpty(customerSettlement.getUrl())) {
if (CollUtil.isNotEmpty(customerSettlement.getFileItems())) {
// 更新交易凭证附件 业务编号
UpdateBusinessFile(customerSettlement);
}
@ -74,7 +74,7 @@ public class CustomerSettlementServiceImpl implements CustomerSettlementService
private void UpdateBusinessFile(CustomerSettlementDO updateReqVO) {
List<String> urls = updateReqVO.getUrl().stream().map(UploadUserFile::getUrl).collect(Collectors.toList());
List<String> urls = updateReqVO.getFileItems().stream().map(UploadUserFile::getUrl).collect(Collectors.toList());
fileApi.updateBusinessFile(urls, updateReqVO.getId().toString());
}
@ -153,13 +153,13 @@ public class CustomerSettlementServiceImpl implements CustomerSettlementService
}
@Override
public void updateConfirm(Long id) {
public void updateConfirm(Long id, Integer status) {
// 校验存在
validateCustomerSettlementExists(id);
// 更新
customerSettlementMapper.updateById(new CustomerSettlementDO()
.setId(id)
.setIsConfirm(1));
.setStatus(status));
}
}

View File

@ -187,7 +187,6 @@ public interface DeptService {
/**
* 获取指定类型的部门列表
*
* @param type 部门类型
* @return 部门列表
*/
@ -195,11 +194,17 @@ public interface DeptService {
/**
* 获取工厂部门
*
* @return 部门列表
*/
List<DeptDO> getFactoryDept();
/**
* 获取部门所属公司信息
* @param deptId 部门编号
* @return 公司信息
*/
DeptDO getCompanyByDept(Long deptId);
/**
* 获取当前登录用户负责的工厂部门
*

View File

@ -404,6 +404,23 @@ public class DeptServiceImpl implements DeptService {
.isNotNull(DeptDO::getFactoryId));
}
@Override
@DataPermission(enable = false)
@Cacheable(cacheNames = RedisKeyConstants.COMPANY_DEPT, key = "#deptId")
public DeptDO getCompanyByDept(Long deptId) {
DeptDO deptDO = deptMapper.selectById(deptId);
if (deptDO.getType().equals(DeptTypeEnum.COMPANY.getValue())) {
return deptDO;
}
// 从缓存中获取所有非虚机构的公司信息
List<DeptDO> companyDOs = this.getCompanyDept(2);
return companyDOs.stream()
.filter(company -> deptDO.getFlag().contains(company.getFlag()))
.findFirst()
.orElse(null);
}
@Override
public List<DeptDO> getFactoryDeptByLeaderId(Long id) {
return deptMapper.selectList(new LambdaQueryWrapperX<DeptDO>()

View File

@ -6,6 +6,8 @@ import cn.iocoder.yudao.module.system.controller.admin.loan.vo.LoanSaveReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.loan.LoanDO;
import javax.validation.Valid;
import java.util.Collection;
import java.util.List;
/**
* 借支管理 Service 接口
@ -41,7 +43,24 @@ public interface LoanService {
/**
* 根据用户编号获取借支管理
* @param userId 用户编号
* @param loanType 借支类型
* @return 借支记录
*/
LoanDO getByUserId(Long userId);
LoanDO getByUserId(Long userId, Integer loanType);
/**
* 根据用户编号集合获取借支管理
* @param userIds 用户编号集合
* @param loanType 借支类型
* @return 借支记录
*/
List<LoanDO> getListByUserId(Collection<Long> userIds, Integer loanType);
/**
* 获取员工截止当前月份的工资借支余额
* @param userId 用户编号集合
* @param month 月份
* @return 借支记录
*/
List<LoanDO> getListByMonth(Collection<Long> userId, String month);
}

View File

@ -2,6 +2,7 @@ package cn.iocoder.yudao.module.system.service.loan;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
import cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX;
import cn.iocoder.yudao.module.system.controller.admin.loan.vo.LoanPageReqVO;
import cn.iocoder.yudao.module.system.controller.admin.loan.vo.LoanSaveReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.loan.LoanDO;
@ -10,6 +11,8 @@ import org.springframework.stereotype.Service;
import org.springframework.validation.annotation.Validated;
import javax.annotation.Resource;
import java.util.Collection;
import java.util.List;
/**
* 借支管理 Service 实现类
@ -27,7 +30,9 @@ public class LoanServiceImpl implements LoanService {
public void createLoan(LoanSaveReqVO createReqVO) {
// 判断该借支用户 是否已存在借支记录
LoanDO loanDO = loanMapper.selectOne(LoanDO::getUserId, createReqVO.getUserId());
LoanDO loanDO = loanMapper.selectOne(new LambdaQueryWrapperX<LoanDO>()
.eq(LoanDO::getUserId, createReqVO.getUserId())
.eq(LoanDO::getLoanType, createReqVO.getLoanType()));
if (loanDO != null) {
// 借支用户已存在借支记录则更新该借支用户记录
LoanDO updateDO = new LoanDO()
@ -38,8 +43,6 @@ public class LoanServiceImpl implements LoanService {
loanMapper.updateById(updateDO);
}else {
// 借支用户不存在借支记录则插入一条新记录
// 插入
LoanDO createDO = BeanUtils.toBean(createReqVO, LoanDO.class);
loanMapper.insert(createDO);
}
@ -56,7 +59,22 @@ public class LoanServiceImpl implements LoanService {
}
@Override
public LoanDO getByUserId(Long userId) {
return loanMapper.selectOne(LoanDO::getUserId, userId);
public LoanDO getByUserId(Long userId, Integer loanType) {
return loanMapper.selectOne(new LambdaQueryWrapperX<LoanDO>()
.eq(LoanDO::getUserId, userId)
.eq(LoanDO::getLoanType, loanType));
}
@Override
public List<LoanDO> getListByUserId(Collection<Long> userIds, Integer loanType) {
return loanMapper.selectList(new LambdaQueryWrapperX<LoanDO>()
.in(LoanDO::getUserId, userIds)
.eq(LoanDO::getLoanType, loanType));
}
@Override
public List<LoanDO> getListByMonth(Collection<Long> userId, String month) {
return loanMapper.selectListByMonth(userId, month);
}
}

View File

@ -8,6 +8,7 @@ import cn.iocoder.yudao.module.system.controller.admin.rental.vo.customer.Rental
import cn.iocoder.yudao.module.system.dal.dataobject.rental.RentalCustomerDO;
import javax.validation.Valid;
import java.math.BigDecimal;
import java.util.List;
/**
@ -38,6 +39,14 @@ public interface RentalCustomerService {
*/
void updateRentalCustomerStatus(RentalCustomerStatusReqVO updateReqVO);
/**
* 更新客户剩余押金金额
*
* @param id 编号
* @param amount 金额
*/
void updateRentalCustomerAmount(Long id, BigDecimal amount);
/**
* 删除租赁客户
*
@ -66,4 +75,11 @@ public interface RentalCustomerService {
* @return 租赁客户列表
*/
List<RentalCustomerDO> getRentalCustomerList();
/**
* 得对应工厂的客户列表
* @param userId 当前登陆用户编号
* @return 客户列表
*/
List<RentalCustomerDO> getListByFactory(Long userId);
}

View File

@ -14,6 +14,7 @@ import org.springframework.validation.annotation.Validated;
import javax.annotation.Resource;
import java.math.BigDecimal;
import java.util.List;
import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
@ -59,6 +60,14 @@ public class RentalCustomerServiceImpl implements RentalCustomerService {
rentalCustomerMapper.updateById(updateObj);
}
@Override
public void updateRentalCustomerAmount(Long id, BigDecimal amount) {
// 校验存在
validateRentalCustomerExists(id);
// 更新
rentalCustomerMapper.updateById(new RentalCustomerDO().setId(id).setAmount(amount));
}
@Override
public void deleteRentalCustomer(Long id) {
// 校验存在
@ -88,4 +97,9 @@ public class RentalCustomerServiceImpl implements RentalCustomerService {
return rentalCustomerMapper.selectList(RentalCustomerDO::getStatus, CommonStatusEnum.ENABLE.getStatus());
}
@Override
public List<RentalCustomerDO> getListByFactory(Long userId) {
return rentalCustomerMapper.selectListByFactory(userId);
}
}

View File

@ -39,6 +39,13 @@ public interface RentalDepositRecordService {
*/
void updateRentalDepositRecord(@Valid RentalDepositRecordSaveReqVO updateReqVO);
/**
* 更新租赁订单押金记录类型
*
* @param updateReqVO 修改信息
| */
void updateRentalDepositRecordType(List<RentalDepositRecordDO> updateReqVO);
/**
* 获得租赁订单押金记录
*

View File

@ -119,9 +119,7 @@ public class RentalDepositRecordServiceImpl implements RentalDepositRecordServic
Long customerId = rentalOrderService.getCustomerIdByOrderNo(createReqVO.getOrderNo());
if (customerId != null) {
// 同步更新客户剩余押金 金额
customerService.updateRentalCustomer(new RentalCustomerSaveReqVO()
.setId(customerId)
.setAmount(customerDepositAmount));
customerService.updateRentalCustomerAmount(customerId, customerDepositAmount);
}
// 返回
@ -155,6 +153,13 @@ public class RentalDepositRecordServiceImpl implements RentalDepositRecordServic
rentalDepositRecordMapper.updateById(updateObj);
}
@Override
public void updateRentalDepositRecordType(List<RentalDepositRecordDO> updateReqVO) {
// 更新
rentalDepositRecordMapper.updateBatch(updateReqVO);
}
private void validateRentalDepositRecordExists(Long id) {
if (rentalDepositRecordMapper.selectById(id) == null) {
throw exception(RENTAL_DEPOSIT_RECORD_NOT_EXISTS);
@ -175,5 +180,4 @@ public class RentalDepositRecordServiceImpl implements RentalDepositRecordServic
public RentalDepositAmountReqVO getRentalDepositRecordAmount(String orderNo, Boolean isUpdate) {
return rentalDepositRecordMapper.selectAmount(orderNo, isUpdate);
}
}

View File

@ -0,0 +1,71 @@
package cn.iocoder.yudao.module.system.service.rental;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordPageReqVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordRespVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordSaveReqVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleStatusReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.rental.RentalDepositRecordDO;
import cn.iocoder.yudao.module.system.dal.dataobject.rental.RentalSaleRecordDO;
import javax.validation.Valid;
import java.util.List;
/**
* 租赁转销售记录 Service 接口
*
* @author 符溶馨
*/
public interface RentalSaleRecordService {
/**
* 创建租赁转销售记录
*
* @param createReqVO 创建信息
* @return 编号
*/
Long createRentalSaleRecord(@Valid RentalSaleRecordSaveReqVO createReqVO);
/**
* 创建租赁转销售记录
*
* @param createReqVO 创建信息
*/
void createBatch(@Valid List<RentalSaleRecordSaveReqVO> createReqVO);
/**
* 更新租赁转销售记录
*
* @param updateReqVO 更新信息
*/
void updateRentalSaleRecord(@Valid RentalSaleStatusReqVO updateReqVO);
/**
* 删除租赁转销售记录
*
* @param id 编号
*/
void deleteRentalSaleRecord(Long id);
/**
* 获得租赁转销售记录
*
* @param id 编号
* @return 租赁转销售记录
*/
RentalSaleRecordDO getRentalSaleRecord(Long id);
/**
* 获得租赁转销售记录分页
*
* @param pageReqVO 分页查询
* @return 租赁转销售记录分页
*/
PageResult<RentalSaleRecordDO> getRentalSaleRecordPage(RentalSaleRecordPageReqVO pageReqVO);
/**
* 获取所有到达周转期的租赁订单押金记录
* @return 订单押金记录
*/
List<RentalSaleRecordRespVO> getSaleDepositRecordList();
}

View File

@ -0,0 +1,113 @@
package cn.iocoder.yudao.module.system.service.rental;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordPageReqVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordRespVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordSaveReqVO;
import cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleStatusReqVO;
import cn.iocoder.yudao.module.system.dal.dataobject.rental.RentalCustomerDO;
import cn.iocoder.yudao.module.system.dal.dataobject.rental.RentalDepositRecordDO;
import cn.iocoder.yudao.module.system.dal.dataobject.rental.RentalSaleRecordDO;
import cn.iocoder.yudao.module.system.dal.mysql.rental.RentalCustomerMapper;
import cn.iocoder.yudao.module.system.dal.mysql.rental.RentalSaleRecordMapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import org.springframework.stereotype.Service;
import org.springframework.validation.annotation.Validated;
import javax.annotation.Resource;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
import static cn.iocoder.yudao.module.system.enums.ErrorCodeConstants.RENTAL_SALE_RECORD_NOT_EXISTS;
/**
* 租赁转销售记录 Service 实现类
*
* @author 符溶馨
*/
@Service
@Validated
public class RentalSaleRecordServiceImpl implements RentalSaleRecordService {
@Resource
private RentalSaleRecordMapper rentalSaleRecordMapper;
@Resource
private RentalCustomerMapper customerMapper;
@Resource
private RentalDepositRecordService depositRecordService;
@Override
public Long createRentalSaleRecord(RentalSaleRecordSaveReqVO createReqVO) {
// 插入
RentalSaleRecordDO rentalSaleRecord = BeanUtils.toBean(createReqVO, RentalSaleRecordDO.class);
rentalSaleRecordMapper.insert(rentalSaleRecord);
// 返回
return rentalSaleRecord.getId();
}
@Override
public void createBatch(List<RentalSaleRecordSaveReqVO> createReqVO) {
// 批量插入
List<RentalSaleRecordDO> rentalSaleDO = BeanUtils.toBean(createReqVO, RentalSaleRecordDO.class);
rentalSaleRecordMapper.insertBatch(rentalSaleDO);
}
@Override
public void updateRentalSaleRecord(RentalSaleStatusReqVO updateReqVO) {
// 校验存在
validateRentalSaleRecordExists(updateReqVO.getId());
// 更新
RentalSaleRecordDO updateObj = BeanUtils.toBean(updateReqVO, RentalSaleRecordDO.class);
rentalSaleRecordMapper.updateById(updateObj);
if (updateReqVO.getStatus() == 1) {
// 同步更新客户押金
customerMapper.update(null, new LambdaUpdateWrapper<RentalCustomerDO>()
.setSql("amount = amount + " + updateReqVO.getAmount())
.eq(RentalCustomerDO::getId, updateReqVO.getCustomerId()));
// 同步更新入账类型
RentalDepositRecordDO depositRecordDO = new RentalDepositRecordDO()
.setId(updateReqVO.getDepositId())
.setType(1);
depositRecordService.updateRentalDepositRecordType(Collections.singletonList(depositRecordDO));
}
}
@Override
public void deleteRentalSaleRecord(Long id) {
// 校验存在
validateRentalSaleRecordExists(id);
// 删除
rentalSaleRecordMapper.deleteById(id);
}
private void validateRentalSaleRecordExists(Long id) {
if (rentalSaleRecordMapper.selectById(id) == null) {
throw exception(RENTAL_SALE_RECORD_NOT_EXISTS);
}
}
@Override
public RentalSaleRecordDO getRentalSaleRecord(Long id) {
return rentalSaleRecordMapper.selectById(id);
}
@Override
public PageResult<RentalSaleRecordDO> getRentalSaleRecordPage(RentalSaleRecordPageReqVO pageReqVO) {
return rentalSaleRecordMapper.selectPage(pageReqVO);
}
@Override
public List<RentalSaleRecordRespVO> getSaleDepositRecordList() {
return rentalSaleRecordMapper.selectSaleDepositRecordList();
}
}

View File

@ -80,9 +80,16 @@ spring:
xxl:
job:
enabled: false # 是否开启调度中心,默认为 true 开启
enabled: true # 是否开启调度中心,默认为 true 开启
admin:
addresses: http://127.0.0.1:9090/xxl-job-admin # 调度中心部署跟地址
executor:
appname: ${spring.application.name} # 执行器 AppName
ip: # 执行器IP [选填]默认为空表示自动获取IP多网卡时可手动设置指定IP该IP不会绑定Host仅作为通讯实用地址信息用于 "执行器注册" 和 "调度中心请求并触发任务"
port: 6666 # ### 执行器端口号 [选填]小于等于0则自动获取默认端口为9999单机部署多个执行器时注意要配置不同执行器端口
logpath: ${user.home}/logs/xxl-job/${spring.application.name} # 执行器运行日志文件存储磁盘路径 # 执行器运行日志文件存储磁盘路径 [选填] :需要对该路径拥有读写权限;为空则使用默认路径;
#accessToken: default_token
logretentiondays: 30 # 执行器日志文件保存天数 [选填] 过期日志自动清理, 限制值大于等于3时生效; 否则, 如-1, 关闭自动清理功能;
--- #################### 服务保障相关配置 ####################

View File

@ -0,0 +1,33 @@
<?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="cn.iocoder.yudao.module.system.dal.mysql.loan.LoanMapper">
<!--
一般情况下,尽可能使用 Mapper 进行 CRUD 增删改查即可。
无法满足的场景,例如说多表关联查询,才使用 XML 编写 SQL。
代码生成器暂时只生成 Mapper XML 文件本身,更多推荐 MybatisX 快速开发插件来生成查询。
文档可见https://www.iocoder.cn/MyBatis/x-plugins/
-->
<select id="selectListByMonth" resultType="cn.iocoder.yudao.module.system.dal.dataobject.loan.LoanDO">
SELECT
a.user_id AS userId,
a.remaining_amount - sum( b.total_money ) AS remainingAmount
FROM
system_loan a
INNER JOIN bpm_oa_loan b ON a.loan_type = b.loan_type
AND a.user_id = b.sf_user_id
WHERE
b.return_date &gt; #{month}
AND b.result = 2
AND a.deleted = 0
AND b.deleted = 0
AND a.loan_type = 1
AND a.user_id IN
<foreach collection="userId" item="item" separator=",">
#{item}
</foreach>
GROUP BY
a.user_id
</select>
</mapper>

View File

@ -0,0 +1,34 @@
<?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="cn.iocoder.yudao.module.system.dal.mysql.rental.RentalCustomerMapper">
<!--
一般情况下,尽可能使用 Mapper 进行 CRUD 增删改查即可。
无法满足的场景,例如说多表关联查询,才使用 XML 编写 SQL。
代码生成器暂时只生成 Mapper XML 文件本身,更多推荐 MybatisX 快速开发插件来生成查询。
文档可见https://www.iocoder.cn/MyBatis/x-plugins/
-->
<select id="selectListByFactory" resultType="cn.iocoder.yudao.module.system.dal.dataobject.rental.RentalCustomerDO">
SELECT DISTINCT
a.*
FROM
system_rental_customer a
INNER JOIN (
SELECT
factory_id AS factoryId
FROM
system_dept
WHERE
leader_user_id = 194 UNION
SELECT
d.factory_id AS factoryId
FROM
system_users u
INNER JOIN system_dept d ON u.dept_id = d.id
WHERE
u.id = 194
) uu ON JSON_CONTAINS( a.factory_ids, CAST( uu.factoryId AS JSON ), '$' )
</select>
</mapper>

View File

@ -11,7 +11,7 @@
<select id="selectAmount" resultType="cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentaldepositrecord.RentalDepositAmountReqVO">
SELECT
COALESCE(SUM( CASE WHEN type = 1 THEN amount END ),0) AS receivedAmount,
COALESCE(SUM( CASE WHEN type = 1 OR type = 3 THEN amount END ),0) AS receivedAmount,
COALESCE(SUM( CASE WHEN type = 2 THEN amount END ),0) AS refundAmount
FROM
system_rental_deposit_record
@ -22,4 +22,5 @@
FOR UPDATE
</if>
</select>
</mapper>

View File

@ -0,0 +1,29 @@
<?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="cn.iocoder.yudao.module.system.dal.mysql.rental.RentalSaleRecordMapper">
<!--
一般情况下,尽可能使用 Mapper 进行 CRUD 增删改查即可。
无法满足的场景,例如说多表关联查询,才使用 XML 编写 SQL。
代码生成器暂时只生成 Mapper XML 文件本身,更多推荐 MybatisX 快速开发插件来生成查询。
文档可见https://www.iocoder.cn/MyBatis/x-plugins/
-->
<select id="selectSaleDepositRecordList" resultType="cn.iocoder.yudao.module.system.controller.admin.rental.vo.rentalsalerecord.RentalSaleRecordRespVO">
SELECT
b.id AS customerId,
a.order_no AS orderNo,
a.amount AS amount,
CURDATE() AS saleDate,
a.id AS depositId,
0 AS status
FROM
system_rental_deposit_record a
INNER JOIN system_rental_order o ON a.order_no = o.order_no
INNER JOIN system_rental_customer b ON b.id = o.customer_id
WHERE
a.type = 1
AND DATE_ADD( a.payment_date, INTERVAL b.turnover_days DAY ) &lt;= CURDATE()
</select>
</mapper>