| | |
| | | import com.ruoyi.common.core.exception.ServiceException; |
| | | import com.ruoyi.user.config.UniversalCodeProperties; |
| | | import com.ruoyi.user.domain.AccountUser; |
| | | import com.ruoyi.user.domain.vo.AccountUserInfoVo; |
| | | import com.ruoyi.user.domain.vo.EarningSummaryVo; |
| | | import com.ruoyi.user.enums.MemberLevelEnum; |
| | | import com.ruoyi.user.mapper.AccountEarningRecordMapper; |
| | | import com.ruoyi.user.mapper.AccountUserMapper; |
| | | |
| | | /** |
| | | * 会员注册服务单元测试 |
| | | * 会员服务单元测试 |
| | | * |
| | | * 覆盖通用推荐码放行、无效/停用推荐码拒绝、正常绑定推荐人三分支。 |
| | | * 覆盖会员注册(通用推荐码放行、无效/停用推荐码拒绝、正常绑定推荐人) |
| | | * 与个人中心会员信息查询(正常返回、入参/会员缺失校验、收益与等级兜底)。 |
| | | * |
| | | * @author hugray |
| | | */ |
| | |
| | | |
| | | @Mock |
| | | private AccountUserMapper accountUserMapper; |
| | | |
| | | @Mock |
| | | private AccountEarningRecordMapper accountEarningRecordMapper; |
| | | |
| | | @Mock |
| | | private UniversalCodeProperties universalCodeProperties; |
| | |
| | | ArgumentCaptor<AccountUser> captor = ArgumentCaptor.forClass(AccountUser.class); |
| | | verify(accountUserMapper).insertAccountUser(captor.capture()); |
| | | AccountUser saved = captor.getValue(); |
| | | assertNull(saved.getReferrerUserId()); |
| | | assertNull(saved.getReferrerId()); |
| | | assertNotNull(saved.getMyReferralCode()); |
| | | // 姓名注册未采集,落库留空(不再以手机号填充) |
| | | assertNull(saved.getNickname()); |
| | | // 通用推荐码注册直接发放 L4 会员等级 |
| | | assertEquals(MemberLevelEnum.L4.getCode(), saved.getSystemLevel()); |
| | | // 通用码不参与推荐人定位 |
| | | verify(accountUserMapper, never()).selectAccountUserByReferralCode(UNIVERSAL_CODE); |
| | | } |
| | |
| | | |
| | | ArgumentCaptor<AccountUser> captor = ArgumentCaptor.forClass(AccountUser.class); |
| | | verify(accountUserMapper).insertAccountUser(captor.capture()); |
| | | assertEquals(100L, captor.getValue().getReferrerUserId()); |
| | | assertEquals(100L, captor.getValue().getReferrerId()); |
| | | // 非通用码注册不设等级,走库默认值 C(普通用户) |
| | | assertNull(captor.getValue().getSystemLevel()); |
| | | } |
| | | |
| | | @Test |
| | | @DisplayName("会员存在时应返回昵称/头像/等级与收益汇总") |
| | | void getAccountUserInfo_shouldReturnProfile_whenMemberExists() |
| | | { |
| | | AccountUser member = new AccountUser(); |
| | | member.setUserId(66L); |
| | | member.setNickname("辉煌G891"); |
| | | member.setPhone("13355555555"); |
| | | member.setAvatar("https://cdn.example.com/a.png"); |
| | | member.setSystemLevel(MemberLevelEnum.L3.getCode()); |
| | | member.setAuthStatus("2"); |
| | | EarningSummaryVo summary = new EarningSummaryVo(1000L, 40000L, 12800000L); |
| | | when(accountUserMapper.selectAccountUserById(66L)).thenReturn(member); |
| | | when(accountEarningRecordMapper.selectEarningSummary(66L)).thenReturn(summary); |
| | | |
| | | AccountUserInfoVo vo = accountUserService.getAccountUserInfo(66L); |
| | | |
| | | assertEquals(66L, vo.getUserId()); |
| | | assertEquals("辉煌G891", vo.getNickname()); |
| | | assertEquals("133****5555", vo.getPhone()); |
| | | assertEquals("https://cdn.example.com/a.png", vo.getAvatar()); |
| | | assertEquals(MemberLevelEnum.L3.getCode(), vo.getMemberLevel()); |
| | | // 认证状态原样下发,供个人中心「实名认证」行徽标回显 |
| | | assertEquals("2", vo.getAuthStatus()); |
| | | assertEquals(1000L, vo.getEarnings().getToday()); |
| | | assertEquals(40000L, vo.getEarnings().getMonth()); |
| | | assertEquals(12800000L, vo.getEarnings().getTotal()); |
| | | } |
| | | |
| | | @Test |
| | | @DisplayName("会员ID为空时应抛出获取会员信息失败") |
| | | void getAccountUserInfo_shouldThrow_whenUserIdNull() |
| | | { |
| | | ServiceException ex = assertThrows(ServiceException.class, |
| | | () -> accountUserService.getAccountUserInfo(null)); |
| | | assertEquals("获取会员信息失败", ex.getMessage()); |
| | | } |
| | | |
| | | @Test |
| | | @DisplayName("会员不存在时应抛出获取会员信息失败") |
| | | void getAccountUserInfo_shouldThrow_whenMemberNotFound() |
| | | { |
| | | when(accountUserMapper.selectAccountUserById(66L)).thenReturn(null); |
| | | |
| | | ServiceException ex = assertThrows(ServiceException.class, |
| | | () -> accountUserService.getAccountUserInfo(66L)); |
| | | assertEquals("获取会员信息失败", ex.getMessage()); |
| | | } |
| | | |
| | | @Test |
| | | @DisplayName("无收益流水时应兜底返回全零汇总") |
| | | void getAccountUserInfo_shouldFallbackZeroEarnings_whenNoRecord() |
| | | { |
| | | AccountUser member = new AccountUser(); |
| | | member.setUserId(66L); |
| | | member.setSystemLevel(MemberLevelEnum.L1.getCode()); |
| | | when(accountUserMapper.selectAccountUserById(66L)).thenReturn(member); |
| | | when(accountEarningRecordMapper.selectEarningSummary(66L)).thenReturn(null); |
| | | |
| | | AccountUserInfoVo vo = accountUserService.getAccountUserInfo(66L); |
| | | |
| | | assertNotNull(vo.getEarnings()); |
| | | assertEquals(0L, vo.getEarnings().getToday()); |
| | | assertEquals(0L, vo.getEarnings().getMonth()); |
| | | assertEquals(0L, vo.getEarnings().getTotal()); |
| | | } |
| | | |
| | | @Test |
| | | @DisplayName("等级为空时应兜底为 C") |
| | | void getAccountUserInfo_shouldFallbackC_whenSystemLevelBlank() |
| | | { |
| | | assertFallbackLevel(null, MemberLevelEnum.C.getCode()); |
| | | assertFallbackLevel("", MemberLevelEnum.C.getCode()); |
| | | } |
| | | |
| | | @Test |
| | | @DisplayName("等级为非法值时应兜底为 C") |
| | | void getAccountUserInfo_shouldFallbackC_whenSystemLevelIllegal() |
| | | { |
| | | assertFallbackLevel("L9", MemberLevelEnum.C.getCode()); |
| | | } |
| | | |
| | | @Test |
| | | @DisplayName("认证状态为空时应兜底为未认证(0)") |
| | | void getAccountUserInfo_shouldFallbackNoneAuthStatus_whenBlank() |
| | | { |
| | | AccountUser member = new AccountUser(); |
| | | member.setUserId(66L); |
| | | member.setSystemLevel(MemberLevelEnum.C.getCode()); |
| | | when(accountUserMapper.selectAccountUserById(66L)).thenReturn(member); |
| | | when(accountEarningRecordMapper.selectEarningSummary(66L)).thenReturn(EarningSummaryVo.zero()); |
| | | |
| | | AccountUserInfoVo vo = accountUserService.getAccountUserInfo(66L); |
| | | |
| | | assertEquals("0", vo.getAuthStatus()); |
| | | } |
| | | |
| | | /** |
| | | * 校验不同等级取值下的等级兜底结果 |
| | | * |
| | | * @param rawLevel 库中原始等级值 |
| | | * @param expectedLevel 期望下发的等级 |
| | | */ |
| | | private void assertFallbackLevel(String rawLevel, String expectedLevel) |
| | | { |
| | | AccountUser member = new AccountUser(); |
| | | member.setUserId(66L); |
| | | member.setSystemLevel(rawLevel); |
| | | when(accountUserMapper.selectAccountUserById(66L)).thenReturn(member); |
| | | when(accountEarningRecordMapper.selectEarningSummary(66L)).thenReturn(EarningSummaryVo.zero()); |
| | | |
| | | AccountUserInfoVo vo = accountUserService.getAccountUserInfo(66L); |
| | | |
| | | assertEquals(expectedLevel, vo.getMemberLevel()); |
| | | } |
| | | |
| | | @Test |
| | | @DisplayName("更新头像时应只写入 avatar 列") |
| | | void updateAvatar_shouldUpdateAvatar_whenValid() |
| | | { |
| | | when(accountUserMapper.updateUserAvatar(any(AccountUser.class))).thenReturn(1); |
| | | |
| | | accountUserService.updateAvatar(66L, "https://cdn.example.com/new.png"); |
| | | |
| | | ArgumentCaptor<AccountUser> captor = ArgumentCaptor.forClass(AccountUser.class); |
| | | verify(accountUserMapper).updateUserAvatar(captor.capture()); |
| | | assertEquals(66L, captor.getValue().getUserId()); |
| | | assertEquals("https://cdn.example.com/new.png", captor.getValue().getAvatar()); |
| | | } |
| | | |
| | | @Test |
| | | @DisplayName("头像地址为空时应抛出提示且不落库") |
| | | void updateAvatar_shouldThrow_whenAvatarBlank() |
| | | { |
| | | ServiceException ex = assertThrows(ServiceException.class, |
| | | () -> accountUserService.updateAvatar(66L, "")); |
| | | |
| | | assertEquals("头像地址不能为空", ex.getMessage()); |
| | | verify(accountUserMapper, never()).updateUserAvatar(any(AccountUser.class)); |
| | | } |
| | | |
| | | @Test |
| | | @DisplayName("头像地址超长时应抛出提示且不落库") |
| | | void updateAvatar_shouldThrow_whenAvatarTooLong() |
| | | { |
| | | String longUrl = "a".repeat(256); |
| | | |
| | | ServiceException ex = assertThrows(ServiceException.class, |
| | | () -> accountUserService.updateAvatar(66L, longUrl)); |
| | | |
| | | assertEquals("头像地址过长", ex.getMessage()); |
| | | verify(accountUserMapper, never()).updateUserAvatar(any(AccountUser.class)); |
| | | } |
| | | |
| | | @Test |
| | | @DisplayName("会员不存在(影响行数为 0)时应抛出更新失败") |
| | | void updateAvatar_shouldThrow_whenMemberNotFound() |
| | | { |
| | | when(accountUserMapper.updateUserAvatar(any(AccountUser.class))).thenReturn(0); |
| | | |
| | | ServiceException ex = assertThrows(ServiceException.class, |
| | | () -> accountUserService.updateAvatar(66L, "https://cdn.example.com/new.png")); |
| | | |
| | | assertEquals("更新头像失败", ex.getMessage()); |
| | | } |
| | | |
| | | @Test |
| | | @DisplayName("会员ID为空时应抛出更新失败") |
| | | void updateAvatar_shouldThrow_whenUserIdNull() |
| | | { |
| | | ServiceException ex = assertThrows(ServiceException.class, |
| | | () -> accountUserService.updateAvatar(null, "https://cdn.example.com/new.png")); |
| | | |
| | | assertEquals("更新头像失败", ex.getMessage()); |
| | | } |
| | | } |