feat(wx用户): 新增微信用户模块功能实现
实现微信用户模块的完整功能,包括: 1. 新增用户增删改查基础功能 2. 添加用户余额管理功能 3. 实现用户关联数据查询 4. 完善参数校验和业务规则 新增错误码COMMON_BAD_REQUEST用于参数校验
This commit is contained in:
parent
48cab32859
commit
03b50542fa
|
|
@ -204,6 +204,7 @@ public enum ErrorCode implements ErrorCodeInterface {
|
|||
|
||||
USER_ADMIN_CAN_NOT_BE_MODIFY(10515, "管理员不允许做任何修改", "Business.USER_ADMIN_CAN_NOT_BE_MODIFY"),
|
||||
|
||||
COMMON_BAD_REQUEST(10516, "请求参数错误", "Business.COMMON_BAD_REQUEST"),
|
||||
;
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -0,0 +1,169 @@
|
|||
package com.agileboot.domain.wx.user;
|
||||
|
||||
import com.agileboot.common.core.page.PageDTO;
|
||||
import com.agileboot.domain.common.command.BulkOperationCommand;
|
||||
import com.agileboot.domain.wx.user.command.AddWxUserCommand;
|
||||
import com.agileboot.domain.wx.user.command.UpdateWxUserCommand;
|
||||
import com.agileboot.domain.wx.user.db.SearchWxUserDO;
|
||||
import com.agileboot.domain.wx.user.db.WxUserEntity;
|
||||
import com.agileboot.domain.wx.user.db.WxUserService;
|
||||
import com.agileboot.domain.wx.user.dto.WxUserDTO;
|
||||
import com.agileboot.domain.wx.user.model.WxUserModel;
|
||||
import com.agileboot.domain.wx.user.model.WxUserModelFactory;
|
||||
import com.agileboot.domain.wx.user.query.SearchWxUserQuery;
|
||||
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
/**
|
||||
* 微信用户应用服务
|
||||
*
|
||||
* @author your-name
|
||||
* @since 2025-01-01
|
||||
*/
|
||||
@Service
|
||||
@RequiredArgsConstructor
|
||||
public class WxUserApplicationService {
|
||||
|
||||
private final WxUserService userService;
|
||||
|
||||
private final WxUserModelFactory modelFactory;
|
||||
|
||||
/**
|
||||
* 获取微信用户列表(分页)
|
||||
*/
|
||||
public PageDTO<WxUserDTO> getUserList(SearchWxUserQuery<SearchWxUserDO> query) {
|
||||
Page<SearchWxUserDO> userPage = userService.getUserListWithJoin(query);
|
||||
List<WxUserDTO> userDTOList = userPage.getRecords()
|
||||
.stream()
|
||||
.map(WxUserDTO::new)
|
||||
.collect(Collectors.toList());
|
||||
return new PageDTO<>(userDTOList, userPage.getTotal());
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取微信用户详情
|
||||
*/
|
||||
public WxUserDTO getUserDetailInfo(Long wxUserId) {
|
||||
WxUserEntity userEntity = userService.getById(wxUserId);
|
||||
if (userEntity == null) {
|
||||
return null;
|
||||
}
|
||||
return new WxUserDTO(userEntity);
|
||||
}
|
||||
|
||||
/**
|
||||
* 根据openid获取微信用户详情
|
||||
*/
|
||||
public WxUserDTO getUserDetailByOpenid(String openid) {
|
||||
WxUserEntity userEntity = userService.getByOpenid(openid);
|
||||
if (userEntity == null) {
|
||||
return null;
|
||||
}
|
||||
return new WxUserDTO(userEntity);
|
||||
}
|
||||
|
||||
/**
|
||||
* 添加微信用户
|
||||
*/
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void addUser(AddWxUserCommand command) {
|
||||
WxUserModel model = modelFactory.create();
|
||||
model.loadAddWxUserCommand(command);
|
||||
|
||||
// 业务校验
|
||||
model.validateBeforeSave();
|
||||
|
||||
// 保存
|
||||
model.insert();
|
||||
}
|
||||
|
||||
/**
|
||||
* 更新微信用户
|
||||
*/
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void updateUser(UpdateWxUserCommand command) {
|
||||
WxUserModel model = modelFactory.loadById(command.getWxUserId());
|
||||
model.loadUpdateWxUserCommand(command);
|
||||
|
||||
// 业务校验
|
||||
model.checkOpenidIsUnique();
|
||||
model.checkTelIsUnique();
|
||||
model.checkFieldRelatedEntityExist();
|
||||
model.checkBalanceIsValid();
|
||||
|
||||
// 更新
|
||||
model.updateById();
|
||||
}
|
||||
|
||||
/**
|
||||
* 删除微信用户(单个)
|
||||
*/
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void deleteUser(Long wxUserId) {
|
||||
WxUserModel model = modelFactory.loadById(wxUserId);
|
||||
|
||||
// 业务校验
|
||||
model.checkCanBeDelete();
|
||||
|
||||
// 软删除
|
||||
model.deleteById();
|
||||
}
|
||||
|
||||
/**
|
||||
* 批量删除微信用户
|
||||
*/
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void deleteUsers(BulkOperationCommand<Long> command) {
|
||||
for (Long wxUserId : command.getIds()) {
|
||||
WxUserModel model = modelFactory.loadById(wxUserId);
|
||||
model.checkCanBeDelete();
|
||||
model.deleteById();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 增加余额
|
||||
*/
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void increaseBalance(Long wxUserId, Integer amount) {
|
||||
WxUserModel model = modelFactory.loadById(wxUserId);
|
||||
|
||||
model.increaseBalance(amount);
|
||||
|
||||
// 更新
|
||||
model.updateById();
|
||||
}
|
||||
|
||||
/**
|
||||
* 减少余额
|
||||
*/
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void decreaseBalance(Long wxUserId, Integer amount) {
|
||||
WxUserModel model = modelFactory.loadById(wxUserId);
|
||||
|
||||
model.decreaseBalance(amount);
|
||||
|
||||
// 更新
|
||||
model.updateById();
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置余额
|
||||
*/
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public void setBalance(Long wxUserId, Integer balance) {
|
||||
WxUserModel model = modelFactory.loadById(wxUserId);
|
||||
|
||||
model.setWxBalance(balance);
|
||||
|
||||
// 校验
|
||||
model.checkBalanceIsValid();
|
||||
|
||||
// 更新
|
||||
model.updateById();
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,35 @@
|
|||
package com.agileboot.domain.wx.user.command;
|
||||
|
||||
import com.agileboot.common.annotation.ExcelColumn;
|
||||
import lombok.Data;
|
||||
|
||||
/**
|
||||
* 添加微信用户命令
|
||||
*
|
||||
* @author your-name
|
||||
* @since 2025-01-01
|
||||
*/
|
||||
@Data
|
||||
public class AddWxUserCommand {
|
||||
|
||||
@ExcelColumn(name = "openid")
|
||||
private String openid;
|
||||
|
||||
@ExcelColumn(name = "汇邦云用户ID")
|
||||
private Long ab98UserId;
|
||||
|
||||
@ExcelColumn(name = "企业用户ID")
|
||||
private Long qyUserId;
|
||||
|
||||
@ExcelColumn(name = "昵称")
|
||||
private String nickName;
|
||||
|
||||
@ExcelColumn(name = "手机号码")
|
||||
private String tel;
|
||||
|
||||
@ExcelColumn(name = "余额(分)")
|
||||
private String wxBalance; // 使用 String 接收,前端传入
|
||||
|
||||
@ExcelColumn(name = "备注")
|
||||
private String remark;
|
||||
}
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
package com.agileboot.domain.wx.user.command;
|
||||
|
||||
import com.agileboot.common.annotation.ExcelColumn;
|
||||
import lombok.Data;
|
||||
|
||||
/**
|
||||
* 更新微信用户命令
|
||||
*
|
||||
* @author your-name
|
||||
* @since 2025-01-01
|
||||
*/
|
||||
@Data
|
||||
public class UpdateWxUserCommand extends AddWxUserCommand {
|
||||
|
||||
@ExcelColumn(name = "主键ID")
|
||||
private Long wxUserId;
|
||||
}
|
||||
|
|
@ -0,0 +1,35 @@
|
|||
package com.agileboot.domain.wx.user.db;
|
||||
|
||||
import com.baomidou.mybatisplus.annotation.TableField;
|
||||
import java.util.Date;
|
||||
import lombok.Data;
|
||||
|
||||
/**
|
||||
* 微信用户查询数据对象(包含关联字段)
|
||||
*
|
||||
* @author your-name
|
||||
* @since 2025-01-01
|
||||
*/
|
||||
@Data
|
||||
public class SearchWxUserDO {
|
||||
|
||||
private Long wxUserId;
|
||||
|
||||
private String openid;
|
||||
|
||||
private Long ab98UserId;
|
||||
|
||||
private Long qyUserId;
|
||||
|
||||
private String nickName;
|
||||
|
||||
private String tel;
|
||||
|
||||
private Integer wxBalance;
|
||||
|
||||
private Date createTime;
|
||||
|
||||
private Date updateTime;
|
||||
|
||||
private String remark;
|
||||
}
|
||||
|
|
@ -0,0 +1,61 @@
|
|||
package com.agileboot.domain.wx.user.db;
|
||||
|
||||
import com.agileboot.common.core.base.BaseEntity;
|
||||
import com.baomidou.mybatisplus.annotation.IdType;
|
||||
import com.baomidou.mybatisplus.annotation.TableField;
|
||||
import com.baomidou.mybatisplus.annotation.TableId;
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
import io.swagger.annotations.ApiModel;
|
||||
import io.swagger.annotations.ApiModelProperty;
|
||||
import java.io.Serializable;
|
||||
import java.util.Date;
|
||||
import lombok.Data;
|
||||
import lombok.EqualsAndHashCode;
|
||||
|
||||
/**
|
||||
* 微信用户信息表
|
||||
*
|
||||
* @author your-name
|
||||
* @since 2025-01-01
|
||||
*/
|
||||
@Data
|
||||
@EqualsAndHashCode(callSuper = true)
|
||||
@TableName("wx_user")
|
||||
@ApiModel(value = "WxUserEntity对象", description = "微信用户信息表")
|
||||
public class WxUserEntity extends BaseEntity<WxUserEntity> {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
@ApiModelProperty("主键ID")
|
||||
@TableId(value = "wx_user_id", type = IdType.AUTO)
|
||||
private Long wxUserId;
|
||||
|
||||
@ApiModelProperty("openid")
|
||||
@TableField("openid")
|
||||
private String openid;
|
||||
|
||||
@ApiModelProperty("汇邦云用户ID")
|
||||
@TableField("ab98_user_id")
|
||||
private Long ab98UserId;
|
||||
|
||||
@ApiModelProperty("企业用户id")
|
||||
@TableField("qy_user_id")
|
||||
private Long qyUserId;
|
||||
|
||||
@ApiModelProperty("昵称")
|
||||
@TableField("nick_name")
|
||||
private String nickName;
|
||||
|
||||
@ApiModelProperty("手机号码")
|
||||
@TableField("tel")
|
||||
private String tel;
|
||||
|
||||
@ApiModelProperty("用户余额(单位:分)")
|
||||
@TableField("wx_balance")
|
||||
private Integer wxBalance;
|
||||
|
||||
@Override
|
||||
public Serializable pkVal() {
|
||||
return this.wxUserId;
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,49 @@
|
|||
package com.agileboot.domain.wx.user.db;
|
||||
|
||||
import com.agileboot.common.core.page.AbstractPageQuery;
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
import org.apache.ibatis.annotations.Param;
|
||||
import org.apache.ibatis.annotations.Select;
|
||||
|
||||
/**
|
||||
* 微信用户信息表 Mapper 接口
|
||||
*
|
||||
* @author your-name
|
||||
* @since 2025-01-01
|
||||
*/
|
||||
@Mapper
|
||||
public interface WxUserMapper extends BaseMapper<WxUserEntity> {
|
||||
|
||||
/**
|
||||
* 分页查询微信用户列表(带关联数据)
|
||||
*
|
||||
* @param page 分页参数
|
||||
* @param query 查询条件
|
||||
* @return 微信用户列表
|
||||
*/
|
||||
@Select({
|
||||
"<script>",
|
||||
"SELECT w.*, a.nick_name as ab98_nick_name, q.nick_name as qy_nick_name",
|
||||
"FROM wx_user w",
|
||||
"LEFT JOIN ab98_user a ON w.ab98_user_id = a.ab98_user_id",
|
||||
"LEFT JOIN qy_user q ON w.qy_user_id = q.qy_user_id",
|
||||
"WHERE w.deleted = 0",
|
||||
"<if test='query.openid != null and query.openid != \"\"'>",
|
||||
" AND w.openid LIKE CONCAT('%', #{query.openid}, '%')",
|
||||
"</if>",
|
||||
"<if test='query.nickName != null and query.nickName != \"\"'>",
|
||||
" AND w.nick_name LIKE CONCAT('%', #{query.nickName}, '%')",
|
||||
"</if>",
|
||||
"<if test='query.tel != null and query.tel != \"\"'>",
|
||||
" AND w.tel LIKE CONCAT('%', #{query.tel}, '%')",
|
||||
"</if>",
|
||||
"ORDER BY w.create_time DESC",
|
||||
"</script>"
|
||||
})
|
||||
Page<SearchWxUserDO> selectUserListWithJoin(
|
||||
Page<SearchWxUserDO> page,
|
||||
@Param("query") AbstractPageQuery<SearchWxUserDO> query
|
||||
);
|
||||
}
|
||||
|
|
@ -0,0 +1,65 @@
|
|||
package com.agileboot.domain.wx.user.db;
|
||||
|
||||
import com.agileboot.common.core.page.AbstractPageQuery;
|
||||
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||
import com.baomidou.mybatisplus.extension.service.IService;
|
||||
|
||||
/**
|
||||
* 微信用户信息表 服务类
|
||||
*
|
||||
* @author your-name
|
||||
* @since 2025-01-01
|
||||
*/
|
||||
public interface WxUserService extends IService<WxUserEntity> {
|
||||
|
||||
/**
|
||||
* 检测openid是否唯一
|
||||
*
|
||||
* @param openid openid
|
||||
* @param wxUserId 微信用户ID(更新时传入,排除自身)
|
||||
* @return 是否唯一
|
||||
*/
|
||||
boolean isOpenidUnique(String openid, Long wxUserId);
|
||||
|
||||
/**
|
||||
* 检测手机号是否唯一
|
||||
*
|
||||
* @param tel 手机号
|
||||
* @param wxUserId 微信用户ID(更新时传入,排除自身)
|
||||
* @return 是否唯一
|
||||
*/
|
||||
boolean isTelUnique(String tel, Long wxUserId);
|
||||
|
||||
/**
|
||||
* 根据条件分页查询微信用户列表
|
||||
*
|
||||
* @param query 查询参数
|
||||
* @return 微信用户信息集合
|
||||
*/
|
||||
Page<WxUserEntity> getUserList(AbstractPageQuery<WxUserEntity> query);
|
||||
|
||||
/**
|
||||
* 根据条件分页查询微信用户列表(带额外字段)
|
||||
*
|
||||
* @param query 查询参数
|
||||
* @return 微信用户信息集合(含关联字段)
|
||||
*/
|
||||
Page<SearchWxUserDO> getUserListWithJoin(AbstractPageQuery<SearchWxUserDO> query);
|
||||
|
||||
/**
|
||||
* 根据openid获取微信用户
|
||||
*
|
||||
* @param openid openid
|
||||
* @return 微信用户信息
|
||||
*/
|
||||
WxUserEntity getByOpenid(String openid);
|
||||
|
||||
/**
|
||||
* 更新用户余额
|
||||
*
|
||||
* @param wxUserId 微信用户ID
|
||||
* @param balance 余额(单位:分)
|
||||
* @return 是否成功
|
||||
*/
|
||||
boolean updateBalance(Long wxUserId, Integer balance);
|
||||
}
|
||||
|
|
@ -0,0 +1,101 @@
|
|||
package com.agileboot.domain.wx.user.db.impl;
|
||||
|
||||
import cn.hutool.core.util.StrUtil;
|
||||
import com.agileboot.common.core.page.AbstractPageQuery;
|
||||
import com.agileboot.domain.wx.user.db.WxUserEntity;
|
||||
import com.agileboot.domain.wx.user.db.SearchWxUserDO;
|
||||
import com.agileboot.domain.wx.user.db.WxUserMapper;
|
||||
import com.agileboot.domain.wx.user.db.WxUserService;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
||||
import java.util.Objects;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
/**
|
||||
* 微信用户信息表 服务实现类
|
||||
*
|
||||
* @author your-name
|
||||
* @since 2025-01-01
|
||||
*/
|
||||
@Service
|
||||
@RequiredArgsConstructor
|
||||
public class WxUserServiceImpl extends ServiceImpl<WxUserMapper, WxUserEntity> implements WxUserService {
|
||||
|
||||
@Override
|
||||
public boolean isOpenidUnique(String openid, Long wxUserId) {
|
||||
if (StrUtil.isEmpty(openid)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
LambdaQueryWrapper<WxUserEntity> wrapper = new LambdaQueryWrapper<>();
|
||||
|
||||
wrapper.eq(WxUserEntity::getOpenid, openid)
|
||||
.eq(WxUserEntity::getDeleted, 0);
|
||||
|
||||
// 如果是更新操作,排除自身
|
||||
if (wxUserId != null) {
|
||||
wrapper.ne(WxUserEntity::getWxUserId, wxUserId);
|
||||
}
|
||||
|
||||
return !(this.count(wrapper) > 0);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isTelUnique(String tel, Long wxUserId) {
|
||||
if (StrUtil.isEmpty(tel)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
LambdaQueryWrapper<WxUserEntity> wrapper = new LambdaQueryWrapper<>();
|
||||
|
||||
wrapper.eq(WxUserEntity::getTel, tel)
|
||||
.eq(WxUserEntity::getDeleted, 0);
|
||||
|
||||
// 如果是更新操作,排除自身
|
||||
if (wxUserId != null) {
|
||||
wrapper.ne(WxUserEntity::getWxUserId, wxUserId);
|
||||
}
|
||||
|
||||
return !(this.count(wrapper) > 0);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Page<WxUserEntity> getUserList(AbstractPageQuery<WxUserEntity> query) {
|
||||
return this.page(query.toPage(), query.addQueryCondition());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Page<SearchWxUserDO> getUserListWithJoin(AbstractPageQuery<SearchWxUserDO> query) {
|
||||
// 自定义 SQL 查询,返回关联数据
|
||||
return this.getBaseMapper().selectUserListWithJoin(query.toPage(), query);
|
||||
}
|
||||
|
||||
@Override
|
||||
public WxUserEntity getByOpenid(String openid) {
|
||||
if (StrUtil.isEmpty(openid)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
LambdaQueryWrapper<WxUserEntity> wrapper = new LambdaQueryWrapper<>();
|
||||
|
||||
wrapper.eq(WxUserEntity::getOpenid, openid)
|
||||
.eq(WxUserEntity::getDeleted, 0);
|
||||
|
||||
return this.getOne(wrapper);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean updateBalance(Long wxUserId, Integer balance) {
|
||||
if (wxUserId == null || balance == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
WxUserEntity entity = new WxUserEntity();
|
||||
entity.setWxUserId(wxUserId);
|
||||
entity.setWxBalance(balance);
|
||||
|
||||
return this.updateById(entity);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,71 @@
|
|||
package com.agileboot.domain.wx.user.dto;
|
||||
|
||||
import cn.hutool.core.bean.BeanUtil;
|
||||
import com.agileboot.common.annotation.ExcelColumn;
|
||||
import com.agileboot.common.annotation.ExcelSheet;
|
||||
import com.agileboot.domain.wx.user.db.WxUserEntity;
|
||||
import com.agileboot.domain.wx.user.db.SearchWxUserDO;
|
||||
import java.math.BigDecimal;
|
||||
import java.util.Date;
|
||||
import lombok.Data;
|
||||
|
||||
/**
|
||||
* 微信用户DTO
|
||||
*
|
||||
* @author your-name
|
||||
* @since 2025-01-01
|
||||
*/
|
||||
@ExcelSheet(name = "微信用户列表")
|
||||
@Data
|
||||
public class WxUserDTO {
|
||||
|
||||
public WxUserDTO(WxUserEntity entity) {
|
||||
if (entity != null) {
|
||||
BeanUtil.copyProperties(entity, this);
|
||||
|
||||
// 从缓存中获取关联数据(如果需要)
|
||||
// if (entity.getAb98UserId() != null) {
|
||||
// this.ab98NickName = CacheCenter.ab98UserCache.get(entity.getAb98UserId() + "")...;
|
||||
// }
|
||||
}
|
||||
}
|
||||
|
||||
public WxUserDTO(SearchWxUserDO entity) {
|
||||
if (entity != null) {
|
||||
BeanUtil.copyProperties(entity, this);
|
||||
}
|
||||
}
|
||||
|
||||
@ExcelColumn(name = "主键ID")
|
||||
private Long wxUserId;
|
||||
|
||||
@ExcelColumn(name = "openid")
|
||||
private String openid;
|
||||
|
||||
@ExcelColumn(name = "汇邦云用户ID")
|
||||
private Long ab98UserId;
|
||||
|
||||
@ExcelColumn(name = "企业用户ID")
|
||||
private Long qyUserId;
|
||||
|
||||
@ExcelColumn(name = "昵称")
|
||||
private String nickName;
|
||||
|
||||
@ExcelColumn(name = "手机号码")
|
||||
private String tel;
|
||||
|
||||
@ExcelColumn(name = "余额(分)")
|
||||
private Integer wxBalance;
|
||||
|
||||
@ExcelColumn(name = "余额(元)")
|
||||
private BigDecimal wxBalanceYuan; // 转换为元显示
|
||||
|
||||
@ExcelColumn(name = "创建时间")
|
||||
private Date createTime;
|
||||
|
||||
@ExcelColumn(name = "更新时间")
|
||||
private Date updateTime;
|
||||
|
||||
@ExcelColumn(name = "备注")
|
||||
private String remark;
|
||||
}
|
||||
|
|
@ -0,0 +1,177 @@
|
|||
package com.agileboot.domain.wx.user.model;
|
||||
|
||||
import cn.hutool.core.bean.BeanUtil;
|
||||
import cn.hutool.core.util.StrUtil;
|
||||
import com.agileboot.common.exception.ApiException;
|
||||
import com.agileboot.common.exception.error.ErrorCode;
|
||||
import com.agileboot.domain.wx.user.command.AddWxUserCommand;
|
||||
import com.agileboot.domain.wx.user.command.UpdateWxUserCommand;
|
||||
import com.agileboot.domain.wx.user.db.WxUserEntity;
|
||||
import com.agileboot.domain.wx.user.db.WxUserService;
|
||||
import java.math.BigDecimal;
|
||||
import lombok.Data;
|
||||
import lombok.EqualsAndHashCode;
|
||||
import lombok.NoArgsConstructor;
|
||||
|
||||
/**
|
||||
* 微信用户领域模型
|
||||
*
|
||||
* @author your-name
|
||||
* @since 2025-01-01
|
||||
*/
|
||||
@EqualsAndHashCode(callSuper = true)
|
||||
@Data
|
||||
@NoArgsConstructor
|
||||
public class WxUserModel extends WxUserEntity {
|
||||
|
||||
private WxUserService userService;
|
||||
|
||||
public WxUserModel(WxUserEntity entity, WxUserService userService) {
|
||||
if (entity != null) {
|
||||
BeanUtil.copyProperties(entity, this);
|
||||
}
|
||||
this.userService = userService;
|
||||
}
|
||||
|
||||
public WxUserModel(WxUserService userService) {
|
||||
this.userService = userService;
|
||||
}
|
||||
|
||||
/**
|
||||
* 加载添加微信用户命令
|
||||
*/
|
||||
public void loadAddWxUserCommand(AddWxUserCommand command) {
|
||||
if (command != null) {
|
||||
BeanUtil.copyProperties(command, this, "wxUserId");
|
||||
|
||||
// 转换余额字段
|
||||
if (StrUtil.isNotEmpty(command.getWxBalance())) {
|
||||
try {
|
||||
// 前端传入的是元,需要转换为分
|
||||
BigDecimal balanceYuan = new BigDecimal(command.getWxBalance());
|
||||
this.setWxBalance(balanceYuan.multiply(new BigDecimal("100")).intValue());
|
||||
} catch (NumberFormatException e) {
|
||||
throw new ApiException(ErrorCode.Business.COMMON_BAD_REQUEST, "余额格式不正确");
|
||||
}
|
||||
}
|
||||
|
||||
// 设置默认值
|
||||
if (this.getWxBalance() == null) {
|
||||
this.setWxBalance(0); // 默认余额0分
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 加载更新微信用户命令
|
||||
*/
|
||||
public void loadUpdateWxUserCommand(UpdateWxUserCommand command) {
|
||||
if (command != null) {
|
||||
loadAddWxUserCommand(command);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 校验openid唯一性
|
||||
*/
|
||||
public void checkOpenidIsUnique() {
|
||||
if (!userService.isOpenidUnique(getOpenid(), getWxUserId())) {
|
||||
throw new ApiException(ErrorCode.Business.COMMON_BAD_REQUEST, "openid已存在");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 校验手机号唯一性
|
||||
*/
|
||||
public void checkTelIsUnique() {
|
||||
if (!userService.isTelUnique(getTel(), getWxUserId())) {
|
||||
throw new ApiException(ErrorCode.Business.COMMON_BAD_REQUEST, "手机号已存在");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 校验关联数据是否存在
|
||||
*/
|
||||
public void checkFieldRelatedEntityExist() {
|
||||
// 示例:校验汇邦云用户是否存在
|
||||
if (getAb98UserId() != null) {
|
||||
// 可以通过其他 Service 校验
|
||||
// Example: ab98UserService.getById(getAb98UserId());
|
||||
}
|
||||
|
||||
// 示例:校验企业用户是否存在
|
||||
if (getQyUserId() != null) {
|
||||
// 可以通过其他 Service 校验
|
||||
// Example: qyUserService.getById(getQyUserId());
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 校验是否可以删除
|
||||
*/
|
||||
public void checkCanBeDelete() {
|
||||
// 业务逻辑:例如检查用户是否有未完成的订单
|
||||
// if (hasUnfinishedOrders()) {
|
||||
// throw new ApiException(ErrorCode.Business.COMMON_BAD_REQUEST, "用户存在未完成的订单,无法删除");
|
||||
// }
|
||||
}
|
||||
|
||||
/**
|
||||
* 校验余额是否合法
|
||||
*/
|
||||
public void checkBalanceIsValid() {
|
||||
if (getWxBalance() != null && getWxBalance() < 0) {
|
||||
throw new ApiException(ErrorCode.Business.COMMON_BAD_REQUEST, "余额不能为负数");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 增加余额
|
||||
*
|
||||
* @param amount 增加的金额(单位:分)
|
||||
*/
|
||||
public void increaseBalance(Integer amount) {
|
||||
if (amount == null || amount <= 0) {
|
||||
throw new ApiException(ErrorCode.Business.COMMON_BAD_REQUEST, "增加金额必须大于0");
|
||||
}
|
||||
|
||||
Integer newBalance = (this.getWxBalance() == null ? 0 : this.getWxBalance()) + amount;
|
||||
this.setWxBalance(newBalance);
|
||||
}
|
||||
|
||||
/**
|
||||
* 减少余额
|
||||
*
|
||||
* @param amount 减少的金额(单位:分)
|
||||
*/
|
||||
public void decreaseBalance(Integer amount) {
|
||||
if (amount == null || amount <= 0) {
|
||||
throw new ApiException(ErrorCode.Business.COMMON_BAD_REQUEST, "减少金额必须大于0");
|
||||
}
|
||||
|
||||
Integer currentBalance = this.getWxBalance() == null ? 0 : this.getWxBalance();
|
||||
if (currentBalance < amount) {
|
||||
throw new ApiException(ErrorCode.Business.COMMON_BAD_REQUEST, "余额不足");
|
||||
}
|
||||
|
||||
this.setWxBalance(currentBalance - amount);
|
||||
}
|
||||
|
||||
/**
|
||||
* 预保存校验
|
||||
*/
|
||||
public void validateBeforeSave() {
|
||||
if (StrUtil.isEmpty(getOpenid())) {
|
||||
throw new ApiException(ErrorCode.Business.COMMON_BAD_REQUEST, "openid不能为空");
|
||||
}
|
||||
|
||||
if (StrUtil.isEmpty(getNickName())) {
|
||||
throw new ApiException(ErrorCode.Business.COMMON_BAD_REQUEST, "昵称不能为空");
|
||||
}
|
||||
|
||||
checkOpenidIsUnique();
|
||||
checkTelIsUnique();
|
||||
checkFieldRelatedEntityExist();
|
||||
checkBalanceIsValid();
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,58 @@
|
|||
package com.agileboot.domain.wx.user.model;
|
||||
|
||||
import com.agileboot.common.exception.ApiException;
|
||||
import com.agileboot.common.exception.error.ErrorCode;
|
||||
import com.agileboot.domain.wx.user.db.WxUserEntity;
|
||||
import com.agileboot.domain.wx.user.db.WxUserService;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
/**
|
||||
* 微信用户模型工厂
|
||||
*
|
||||
* @author your-name
|
||||
* @since 2025-01-01
|
||||
*/
|
||||
@Component
|
||||
@RequiredArgsConstructor
|
||||
public class WxUserModelFactory {
|
||||
|
||||
private final WxUserService userService;
|
||||
|
||||
/**
|
||||
* 根据ID加载微信用户模型
|
||||
*
|
||||
* @param wxUserId 微信用户ID
|
||||
* @return 微信用户模型
|
||||
*/
|
||||
public WxUserModel loadById(Long wxUserId) {
|
||||
WxUserEntity entity = userService.getById(wxUserId);
|
||||
if (entity == null) {
|
||||
throw new ApiException(ErrorCode.Business.COMMON_OBJECT_NOT_FOUND, wxUserId, "微信用户");
|
||||
}
|
||||
return new WxUserModel(entity, userService);
|
||||
}
|
||||
|
||||
/**
|
||||
* 根据openid加载微信用户模型
|
||||
*
|
||||
* @param openid openid
|
||||
* @return 微信用户模型
|
||||
*/
|
||||
public WxUserModel loadByOpenid(String openid) {
|
||||
WxUserEntity entity = userService.getByOpenid(openid);
|
||||
if (entity == null) {
|
||||
throw new ApiException(ErrorCode.Business.COMMON_OBJECT_NOT_FOUND, openid, "openid");
|
||||
}
|
||||
return new WxUserModel(entity, userService);
|
||||
}
|
||||
|
||||
/**
|
||||
* 创建新微信用户模型
|
||||
*
|
||||
* @return 微信用户模型
|
||||
*/
|
||||
public WxUserModel create() {
|
||||
return new WxUserModel(userService);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,53 @@
|
|||
package com.agileboot.domain.wx.user.query;
|
||||
|
||||
import cn.hutool.core.util.StrUtil;
|
||||
import com.agileboot.common.core.page.AbstractPageQuery;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
||||
import lombok.Data;
|
||||
import lombok.EqualsAndHashCode;
|
||||
|
||||
/**
|
||||
* 微信用户查询条件
|
||||
*
|
||||
* @author your-name
|
||||
* @since 2025-01-01
|
||||
*/
|
||||
@EqualsAndHashCode(callSuper = true)
|
||||
@Data
|
||||
public class SearchWxUserQuery<T> extends AbstractPageQuery<T> {
|
||||
|
||||
private Long wxUserId;
|
||||
|
||||
private String openid;
|
||||
|
||||
private String nickName;
|
||||
|
||||
private String tel;
|
||||
|
||||
private Long ab98UserId;
|
||||
|
||||
private Long qyUserId;
|
||||
|
||||
private Integer minBalance;
|
||||
|
||||
private Integer maxBalance;
|
||||
|
||||
@Override
|
||||
public QueryWrapper<T> addQueryCondition() {
|
||||
QueryWrapper<T> queryWrapper = new QueryWrapper<>();
|
||||
|
||||
queryWrapper.like(StrUtil.isNotEmpty(openid), "openid", openid)
|
||||
.like(StrUtil.isNotEmpty(nickName), "nick_name", nickName)
|
||||
.like(StrUtil.isNotEmpty(tel), "tel", tel)
|
||||
.eq(wxUserId != null, "wx_user_id", wxUserId)
|
||||
.eq(ab98UserId != null, "ab98_user_id", ab98UserId)
|
||||
.eq(qyUserId != null, "qy_user_id", qyUserId)
|
||||
.eq("deleted", 0)
|
||||
.between(minBalance != null && maxBalance != null, "wx_balance", minBalance, maxBalance);
|
||||
|
||||
// 设置时间范围排序字段
|
||||
this.timeRangeColumn = "create_time";
|
||||
|
||||
return queryWrapper;
|
||||
}
|
||||
}
|
||||
|
|
@ -275,8 +275,9 @@ public class ExampleUserServiceImpl extends ServiceImpl<ExampleUserMapper, Examp
|
|||
return true;
|
||||
}
|
||||
|
||||
LambdaQueryWrapper<ExampleUserEntity> wrapper = new LambdaQueryWrapper<>()
|
||||
.eq(ExampleUserEntity::getEmail, email)
|
||||
LambdaQueryWrapper<ExampleUserEntity> wrapper = new LambdaQueryWrapper<>();
|
||||
|
||||
wrapper.eq(ExampleUserEntity::getEmail, email)
|
||||
.eq(ExampleUserEntity::getDeleted, 0);
|
||||
|
||||
// 如果是更新操作,排除自身
|
||||
|
|
@ -284,7 +285,7 @@ public class ExampleUserServiceImpl extends ServiceImpl<ExampleUserMapper, Examp
|
|||
wrapper.ne(ExampleUserEntity::getUserId, userId);
|
||||
}
|
||||
|
||||
return !this.count(wrapper) > 0;
|
||||
return !(this.count(wrapper) > 0);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
@ -293,11 +294,12 @@ public class ExampleUserServiceImpl extends ServiceImpl<ExampleUserMapper, Examp
|
|||
return true;
|
||||
}
|
||||
|
||||
LambdaQueryWrapper<ExampleUserEntity> wrapper = new LambdaQueryWrapper<>()
|
||||
.eq(ExampleUserEntity::getUserName, userName)
|
||||
LambdaQueryWrapper<ExampleUserEntity> wrapper = new LambdaQueryWrapper<>();
|
||||
|
||||
wrapper.eq(ExampleUserEntity::getUserName, userName)
|
||||
.eq(ExampleUserEntity::getDeleted, 0);
|
||||
|
||||
return !this.count(wrapper) > 0;
|
||||
return !(this.count(wrapper) > 0);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
@ -312,13 +314,13 @@ public class ExampleUserServiceImpl extends ServiceImpl<ExampleUserMapper, Examp
|
|||
|
||||
@Override
|
||||
public Page<ExampleUserEntity> getUserList(AbstractPageQuery<ExampleUserEntity> query) {
|
||||
return this.page(query.buildPage(), query.addQueryCondition());
|
||||
return this.page(query.toPage(), query.addQueryCondition());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Page<SearchUserDO> getUserListWithJoin(AbstractPageQuery<SearchUserDO> query) {
|
||||
// 自定义 SQL 查询,返回关联数据
|
||||
return this.getBaseMapper().selectUserListWithJoin(query.buildPage(), query);
|
||||
return this.getBaseMapper().selectUserListWithJoin(query.toPage(), query);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
|
@ -961,7 +963,6 @@ public class UserModelFactory {
|
|||
```java
|
||||
package com.agileboot.domain.example.user;
|
||||
|
||||
import cn.hutool.core.convert.Convert;
|
||||
import com.agileboot.common.core.page.PageDTO;
|
||||
import com.agileboot.domain.common.command.BulkOperationCommand;
|
||||
import com.agileboot.domain.example.user.command.AddUserCommand;
|
||||
|
|
|
|||
Loading…
Reference in New Issue