feat(用户): 添加微信用户信息查询功能

新增微信用户相关字段及查询接口,包括:
1. 在用户实体中添加微信用户ID、openid和昵称字段
2. 新增带微信信息的用户列表查询接口
3. 实现微信用户信息与现有用户系统的关联查询
4. 优化身份证和手机号的脱敏处理逻辑
5. 添加相关SQL表结构定义
This commit is contained in:
dzq 2025-12-04 14:53:30 +08:00
parent 796018aa32
commit fa395bd51e
9 changed files with 180 additions and 4 deletions

View File

@ -56,6 +56,13 @@ public class Ab98UserController extends BaseController {
return ResponseDTO.ok(page);
}
@Operation(summary = "带微信信息的用户列表")
@GetMapping("/withWx")
public ResponseDTO<PageDTO<Ab98UserDTO>> listWithWx(SearchAb98UserQuery<Ab98UserEntity> query) {
PageDTO<Ab98UserDTO> page = userApplicationService.getUserListWithWx(query);
return ResponseDTO.ok(page);
}
@Operation(summary = "用户详情")
@GetMapping("/detail/{id}")
public ResponseDTO<Ab98UserDetailDTO> detail(@PathVariable Long id, String corpid) {

View File

@ -55,6 +55,14 @@ public class Ab98UserApplicationService {
return new PageDTO<>(dtoList, page.getTotal());
}
public PageDTO<Ab98UserDTO> getUserListWithWx(SearchAb98UserQuery<Ab98UserEntity> query) {
Page<Ab98UserEntity> page = userService.getUserListWithWx(query);
List<Ab98UserDTO> dtoList = page.getRecords().stream()
.map(Ab98UserDTO::new)
.collect(Collectors.toList());
return new PageDTO<>(dtoList, page.getTotal());
}
public void addUser(AddAb98UserCommand command) {
Ab98UserModel model = userModelFactory.create();
model.loadAddCommand(command);

View File

@ -91,6 +91,18 @@ public class Ab98UserEntity extends BaseEntity<Ab98UserEntity> {
@TableField(exist = false)
private Long balanceLimit;
@ApiModelProperty("微信用户ID")
@TableField(exist = false)
private Long wxUserId;
@ApiModelProperty("微信用户openid")
@TableField(exist = false)
private String wxUserOpenid;
@ApiModelProperty("微信用户昵称")
@TableField(exist = false)
private String wxNickName;
@Override
public Serializable pkVal() {

View File

@ -60,6 +60,23 @@ public interface Ab98UserMapper extends BaseMapper<Ab98UserEntity> {
@Param(Constants.WRAPPER) Wrapper<Ab98UserEntity> queryWrapper
);
@Select("SELECT * FROM (" +
"SELECT DISTINCT u.ab98_user_id, u.openid, u.userid, u.qy_user_id, u.name, u.tel, u.idnum, u.sex, u.face_img, u.idcard_front, u.idcard_back, u.address, u.registered, u.creator_id, u.create_time, u.updater_id, u.update_time, u.deleted, u.ab98_balance, ub.balance, ub.use_balance, ub.balance_limit, w.wx_user_id, w.openid as wx_user_openid, w.nick_name as wx_nick_name " +
"FROM ab98_user u " +
"LEFT JOIN ab98_user_tag t ON u.ab98_user_id = t.ab98_user_id " +
"LEFT JOIN user_balance ub ON u.ab98_user_id = ub.ab98_user_id " +
"LEFT JOIN wx_user w ON u.ab98_user_id = w.ab98_user_id " +
"${ew.customSqlSegment}" +
" UNION ALL " +
"SELECT NULL as ab98_user_id, NULL as openid, NULL as userid, NULL as qy_user_id, NULL as name, NULL as tel, NULL as idnum, NULL as sex, NULL as face_img, NULL as idcard_front, NULL as idcard_back, NULL as address, NULL as registered, NULL as creator_id, w.create_time as create_time, NULL as updater_id, w.update_time as update_time, NULL as deleted, NULL as ab98_balance, NULL as balance, NULL as use_balance, NULL as balance_limit, w.wx_user_id, w.openid as wx_user_openid, w.nick_name as wx_nick_name " +
"FROM wx_user w " +
"WHERE w.ab98_user_id IS NULL" +
") t ORDER BY create_time DESC")
Page<Ab98UserEntity> getUserListWithWx(
Page<Ab98UserEntity> page,
@Param(Constants.WRAPPER) Wrapper<Ab98UserEntity> queryWrapper
);
@Select("SELECT DISTINCT u.*, ub.balance, ub.use_balance, ub.balance_limit " +
"FROM ab98_user u " +
"LEFT JOIN user_balance ub ON u.ab98_user_id = ub.ab98_user_id " +

View File

@ -20,6 +20,8 @@ import java.util.List;
public interface Ab98UserService extends IService<Ab98UserEntity> {
Page<Ab98UserEntity> getUserListWithTagFilter(AbstractPageQuery<Ab98UserEntity> query);
Page<Ab98UserEntity> getUserListWithWx(AbstractPageQuery<Ab98UserEntity> query);
List<Ab98UserEntity> getUserListWithBalance(Wrapper<Ab98UserEntity> wrapper);
List<Ab98UserEntity> selectAll();

View File

@ -26,6 +26,11 @@ public class Ab98UserServiceImpl extends ServiceImpl<Ab98UserMapper, Ab98UserEnt
return baseMapper.getUserListWithTagFilter(query.toPage(), query.toQueryWrapper());
}
@Override
public Page<Ab98UserEntity> getUserListWithWx(AbstractPageQuery<Ab98UserEntity> query) {
return baseMapper.getUserListWithWx(query.toPage(), query.toQueryWrapper());
}
@Override
public List<Ab98UserEntity> selectAll() {
LambdaQueryWrapper<Ab98UserEntity> wrapper = new LambdaQueryWrapper<>();

View File

@ -16,11 +16,30 @@ public class Ab98UserDTO {
if (entity != null) {
BeanUtil.copyProperties(entity, this);
this.registeredStatus = entity.getRegistered() ? "已注册" : "未注册";
this.registeredStatus = entity.getRegistered() != null && entity.getRegistered() ? "已注册" : "未注册";
// 处理身份证号码隐藏中间8位
if (this.idnum != null && this.idnum.length() >= 10) {
this.idnum = this.idnum.substring(0, 6) + "********" + this.idnum.substring(this.idnum.length() - 4);
// 处理身份证号码隐藏除前4位和后2位之外的所有字符
if (this.idnum != null && this.idnum.length() >= 6) {
int hiddenLength = this.idnum.length() - 6; // 需要隐藏的字符数
if (hiddenLength > 0) {
StringBuilder stars = new StringBuilder();
for (int i = 0; i < hiddenLength; i++) {
stars.append("*");
}
this.idnum = this.idnum.substring(0, 4) + stars.toString() + this.idnum.substring(this.idnum.length() - 2);
}
}
// 处理手机号码隐藏除前3位和后2位之外的所有字符
if (this.tel != null && this.tel.length() >= 5) {
int hiddenLength = this.tel.length() - 5; // 需要隐藏的字符数
if (hiddenLength > 0) {
StringBuilder stars = new StringBuilder();
for (int i = 0; i < hiddenLength; i++) {
stars.append("*");
}
this.tel = this.tel.substring(0, 3) + stars.toString() + this.tel.substring(this.tel.length() - 2);
}
}
}
}
@ -70,6 +89,15 @@ public class Ab98UserDTO {
@ExcelColumn(name = "余额限制user_balance表单位")
private Long balanceLimit;
@ExcelColumn(name = "微信用户ID")
private Long wxUserId;
@ExcelColumn(name = "微信用户openid")
private String wxUserOpenid;
@ExcelColumn(name = "微信用户昵称")
private String wxNickName;
@ExcelColumn(name = "注册状态")
private String registeredStatus;

View File

@ -23,6 +23,7 @@ public class SearchAb98UserQuery<T> extends AbstractPageQuery<T> {
private Date endTime;
private String tagName;
private String corpid;
private String wxUserOpenid;
@Override
public QueryWrapper<T> addQueryCondition() {
@ -41,6 +42,11 @@ public class SearchAb98UserQuery<T> extends AbstractPageQuery<T> {
.eq(StrUtil.isNotEmpty(corpid), "ub.corpid", corpid)
.between(startTime != null && endTime != null, "u.create_time", startTime, endTime);
// 添加微信用户openid查询条件
if (StrUtil.isNotEmpty(wxUserOpenid)) {
queryWrapper.apply("wx_user_openid = {0}", wxUserOpenid);
}
this.timeRangeColumn = "create_time";
return queryWrapper;

91
doc/sql/wxUser.sql Normal file
View File

@ -0,0 +1,91 @@
-- wxshop.ab98_user definition
CREATE TABLE `ab98_user` (
`ab98_user_id` bigint NOT NULL AUTO_INCREMENT COMMENT '主键ID',
`openid` varchar(32) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT 'openid',
`userid` varchar(100) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '汇邦云用户唯一ID',
`qy_user_id` bigint DEFAULT NULL COMMENT '企业用户id',
`name` varchar(50) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '真实姓名',
`tel` varchar(20) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '手机号码',
`idnum` varchar(20) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '身份证号码',
`sex` char(8) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '性别(男 女)',
`face_img` varchar(500) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '人脸照片地址',
`idcard_front` varchar(500) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '身份证正面地址',
`idcard_back` varchar(500) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '身份证背面地址',
`address` varchar(200) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '身份证登记地址',
`registered` tinyint(1) NOT NULL DEFAULT '0' COMMENT '是否已注册0未注册 1已注册',
`creator_id` bigint DEFAULT '0' COMMENT '创建者ID',
`create_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
`updater_id` bigint DEFAULT '0' COMMENT '更新者ID',
`update_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
`deleted` tinyint(1) NOT NULL DEFAULT '0' COMMENT '删除标志0存在 1删除',
`ab98_balance` int NOT NULL DEFAULT '0' COMMENT '用户余额(单位:分)',
PRIMARY KEY (`ab98_user_id`),
UNIQUE KEY `uk_idnum` (`idnum`),
KEY `idx_openid` (`openid`),
KEY `idx_tel` (`tel`),
KEY `idx_name` (`name`)
) ENGINE=InnoDB AUTO_INCREMENT=87 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='汇邦云用户信息表';
-- wxshop.user_balance definition
CREATE TABLE `user_balance` (
`user_balance_id` bigint NOT NULL AUTO_INCREMENT COMMENT '主键ID',
`corpid` varchar(50) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '企业微信id',
`openid` varchar(32) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT 'openid',
`ab98_user_id` bigint NOT NULL COMMENT '汇邦云用户ID',
`qy_user_id` bigint DEFAULT NULL COMMENT '企业用户id',
`balance` bigint NOT NULL DEFAULT '0' COMMENT '用户余额(单位:分)',
`use_balance` bigint NOT NULL DEFAULT '0' COMMENT '用户余额(单位:分)',
`balance_limit` bigint NOT NULL DEFAULT '0' COMMENT '用户余额(单位:分)',
`creator_id` bigint DEFAULT '0' COMMENT '创建者ID',
`create_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
`updater_id` bigint DEFAULT '0' COMMENT '更新者ID',
`update_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
`deleted` tinyint(1) NOT NULL DEFAULT '0' COMMENT '删除标志0存在 1删除',
PRIMARY KEY (`user_balance_id`),
UNIQUE KEY `uk_corpid_user` (`corpid`,`ab98_user_id`),
KEY `idx_openid` (`openid`),
KEY `idx_ab98_user_id` (`ab98_user_id`),
KEY `idx_corpid` (`corpid`)
) ENGINE=InnoDB AUTO_INCREMENT=137 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='用户余额表';
-- wxshop.wx_user definition
CREATE TABLE `wx_user` (
`wx_user_id` bigint NOT NULL AUTO_INCREMENT COMMENT '主键ID',
`openid` varchar(32) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT 'openid',
`ab98_user_id` bigint DEFAULT NULL COMMENT '汇邦云用户ID',
`qy_user_id` bigint DEFAULT NULL COMMENT '企业用户id',
`nick_name` varchar(50) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '昵称',
`tel` varchar(20) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '手机号码',
`wx_balance` int NOT NULL DEFAULT '0' COMMENT '用户余额(单位:分)',
`creator_id` bigint DEFAULT '0' COMMENT '创建者ID',
`create_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
`updater_id` bigint DEFAULT '0' COMMENT '更新者ID',
`update_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
`deleted` tinyint(1) NOT NULL DEFAULT '0' COMMENT '删除标志0存在 1删除',
PRIMARY KEY (`wx_user_id`),
KEY `idx_openid` (`openid`),
KEY `idx_tel` (`tel`),
KEY `idx_nick_name` (`nick_name`)
) ENGINE=InnoDB AUTO_INCREMENT=151 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='微信用户信息表';
-- wxshop.ab98_user_tag definition
CREATE TABLE `ab98_user_tag` (
`tag_id` bigint NOT NULL AUTO_INCREMENT COMMENT '标签ID',
`ab98_user_id` bigint NOT NULL COMMENT '关联用户ID',
`tag_name` varchar(50) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '标签名称',
`creator_id` bigint DEFAULT '0' COMMENT '创建者ID',
`create_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
`updater_id` bigint DEFAULT '0' COMMENT '更新者ID',
`update_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
`deleted` tinyint(1) NOT NULL DEFAULT '0' COMMENT '删除标志0存在 1删除',
PRIMARY KEY (`tag_id`),
KEY `idx_user` (`ab98_user_id`),
CONSTRAINT `fk_tag_user` FOREIGN KEY (`ab98_user_id`) REFERENCES `ab98_user` (`ab98_user_id`)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='用户标签表';