fix: random order clerk visibility rules
Some checks failed
Build and Push Backend / docker (push) Failing after 12s
Some checks failed
Build and Push Backend / docker (push) Failing after 12s
This commit is contained in:
@@ -477,13 +477,27 @@ public class PlayOrderInfoServiceImpl extends ServiceImpl<PlayOrderInfoMapper, P
|
||||
}
|
||||
}
|
||||
|
||||
// Privacy protection: Hide customer info for pending random orders
|
||||
if (OrderConstant.PlaceType.RANDOM.getCode().equals(returnVo.getPlaceType())
|
||||
&& OrderStatus.PENDING.getCode().equals(returnVo.getOrderStatus())) {
|
||||
// Privacy protection for random orders:
|
||||
// 1) Pending random orders: hide customer info completely.
|
||||
// 2) Random orders accepted by another clerk: hide customer info and mask status.
|
||||
boolean isRandomOrder = OrderConstant.PlaceType.RANDOM.getCode().equals(returnVo.getPlaceType());
|
||||
String orderStatus = returnVo.getOrderStatus();
|
||||
String acceptBy = returnVo.getAcceptBy();
|
||||
boolean isPending = OrderStatus.PENDING.getCode().equals(orderStatus);
|
||||
boolean acceptedByOtherClerk = StringUtils.isNotEmpty(acceptBy) && !acceptBy.equals(clerkId) && !isPending;
|
||||
|
||||
if (isRandomOrder && isPending) {
|
||||
returnVo.setWeiChatCode("");
|
||||
returnVo.setCustomNickname("匿名用户");
|
||||
returnVo.setCustomAvatar("");
|
||||
returnVo.setCustomId("");
|
||||
} else if (isRandomOrder && acceptedByOtherClerk) {
|
||||
returnVo.setWeiChatCode("");
|
||||
returnVo.setCustomNickname("匿名用户");
|
||||
returnVo.setCustomAvatar("");
|
||||
returnVo.setCustomId("");
|
||||
// Hide concrete status when viewing another clerk's random order
|
||||
returnVo.setOrderStatus("");
|
||||
}
|
||||
|
||||
if (returnVo.getEstimatedRevenue() == null) {
|
||||
|
||||
@@ -207,6 +207,106 @@ class WxOrderInfoControllerApiTest extends WxCustomOrderApiTestSupport {
|
||||
assertThat(data.path("customAvatar").asText()).isEmpty();
|
||||
}
|
||||
|
||||
@Test
|
||||
void queryByIdForAcceptedRandomOrderOwnedByCurrentClerkRetainsCustomerInfoAndStatus() throws Exception {
|
||||
String marker = "random-owned-" + LocalDateTime.now();
|
||||
String orderId = createRandomOrder(marker);
|
||||
|
||||
// Mark the random order as accepted by the current test clerk
|
||||
ensureTenantContext();
|
||||
playOrderInfoService.lambdaUpdate()
|
||||
.eq(PlayOrderInfoEntity::getId, orderId)
|
||||
.set(PlayOrderInfoEntity::getAcceptBy, ApiTestDataSeeder.DEFAULT_CLERK_ID)
|
||||
.set(PlayOrderInfoEntity::getOrderStatus, OrderConstant.OrderStatus.ACCEPTED.getCode())
|
||||
.update();
|
||||
|
||||
MvcResult result = mockMvc.perform(get("/wx/clerk/order/queryById")
|
||||
.param("id", orderId)
|
||||
.header(USER_HEADER, DEFAULT_USER)
|
||||
.header(TENANT_HEADER, DEFAULT_TENANT)
|
||||
.header(Constants.CLERK_USER_LOGIN_TOKEN, Constants.TOKEN_PREFIX + clerkToken))
|
||||
.andExpect(status().isOk())
|
||||
.andExpect(jsonPath("$.code").value(200))
|
||||
.andReturn();
|
||||
|
||||
JsonNode data = mapper.readTree(result.getResponse().getContentAsString()).path("data");
|
||||
assertThat(data.path("placeType").asText()).isEqualTo(OrderConstant.PlaceType.RANDOM.getCode());
|
||||
assertThat(data.path("acceptBy").asText()).isEqualTo(ApiTestDataSeeder.DEFAULT_CLERK_ID);
|
||||
assertThat(data.path("orderStatus").asText()).isEqualTo(OrderConstant.OrderStatus.ACCEPTED.getCode());
|
||||
// For the owning clerk, customer info should not be forced to anonymous
|
||||
String nickname = data.path("customNickname").asText();
|
||||
assertThat(nickname).isNotEmpty();
|
||||
assertThat(nickname).isNotIn("匿名用户", "å¿åç¨æ·");
|
||||
assertThat(data.path("weiChatCode").asText())
|
||||
.withFailMessage("Owner clerk should see customer wechat for accepted random order")
|
||||
.isNotEmpty();
|
||||
}
|
||||
|
||||
@Test
|
||||
void queryByIdForRandomOrderAcceptedByAnotherClerkHidesCustomerInfoAndOrderStatus() throws Exception {
|
||||
String marker = "random-other-clerk-" + LocalDateTime.now();
|
||||
String orderId = createRandomOrder(marker);
|
||||
|
||||
ensureTenantContext();
|
||||
playOrderInfoService.lambdaUpdate()
|
||||
.eq(PlayOrderInfoEntity::getId, orderId)
|
||||
.set(PlayOrderInfoEntity::getAcceptBy, OTHER_CLERK_ID)
|
||||
.set(PlayOrderInfoEntity::getOrderStatus, OrderConstant.OrderStatus.ACCEPTED.getCode())
|
||||
.update();
|
||||
|
||||
MvcResult result = mockMvc.perform(get("/wx/clerk/order/queryById")
|
||||
.param("id", orderId)
|
||||
.header(USER_HEADER, DEFAULT_USER)
|
||||
.header(TENANT_HEADER, DEFAULT_TENANT)
|
||||
.header(Constants.CLERK_USER_LOGIN_TOKEN, Constants.TOKEN_PREFIX + clerkToken))
|
||||
.andExpect(status().isOk())
|
||||
.andExpect(jsonPath("$.code").value(200))
|
||||
.andReturn();
|
||||
|
||||
JsonNode data = mapper.readTree(result.getResponse().getContentAsString()).path("data");
|
||||
assertThat(data.path("placeType").asText()).isEqualTo(OrderConstant.PlaceType.RANDOM.getCode());
|
||||
assertThat(data.path("acceptBy").asText()).isEqualTo(OTHER_CLERK_ID);
|
||||
// Order status must be masked for random orders owned by another clerk
|
||||
assertThat(data.path("orderStatus").asText()).isEmpty();
|
||||
assertThat(data.path("weiChatCode").asText()).isEmpty();
|
||||
assertThat(data.path("customId").asText()).isEmpty();
|
||||
String nickname = data.path("customNickname").asText();
|
||||
assertThat(nickname.equals("匿名用户") || "å¿åç¨æ·".equals(nickname)).isTrue();
|
||||
assertThat(data.path("customAvatar").asText()).isEmpty();
|
||||
}
|
||||
|
||||
@Test
|
||||
void queryByIdForNonRandomOrderAcceptedByAnotherClerkDoesNotMaskStatus() throws Exception {
|
||||
String marker = "specified-other-clerk-" + LocalDateTime.now();
|
||||
String orderId = createRandomOrder(marker);
|
||||
|
||||
// Re-tag the order as a specified order to ensure non-random logic
|
||||
ensureTenantContext();
|
||||
playOrderInfoService.lambdaUpdate()
|
||||
.eq(PlayOrderInfoEntity::getId, orderId)
|
||||
.set(PlayOrderInfoEntity::getPlaceType, OrderConstant.PlaceType.SPECIFIED.getCode())
|
||||
.set(PlayOrderInfoEntity::getAcceptBy, OTHER_CLERK_ID)
|
||||
.set(PlayOrderInfoEntity::getOrderStatus, OrderConstant.OrderStatus.ACCEPTED.getCode())
|
||||
.update();
|
||||
|
||||
MvcResult result = mockMvc.perform(get("/wx/clerk/order/queryById")
|
||||
.param("id", orderId)
|
||||
.header(USER_HEADER, DEFAULT_USER)
|
||||
.header(TENANT_HEADER, DEFAULT_TENANT)
|
||||
.header(Constants.CLERK_USER_LOGIN_TOKEN, Constants.TOKEN_PREFIX + clerkToken))
|
||||
.andExpect(status().isOk())
|
||||
.andExpect(jsonPath("$.code").value(200))
|
||||
.andReturn();
|
||||
|
||||
JsonNode data = mapper.readTree(result.getResponse().getContentAsString()).path("data");
|
||||
assertThat(data.path("placeType").asText()).isEqualTo(OrderConstant.PlaceType.SPECIFIED.getCode());
|
||||
// Status should remain the real value for non-random orders
|
||||
assertThat(data.path("orderStatus").asText()).isEqualTo(OrderConstant.OrderStatus.ACCEPTED.getCode());
|
||||
// We still expect customer info to not be forcibly anonymized by the random-order privacy rules
|
||||
String nickname = data.path("customNickname").asText();
|
||||
assertThat(nickname).isNotIn("匿名用户", "å¿åç¨æ·");
|
||||
}
|
||||
|
||||
@Test
|
||||
void clerkOrderListHidesCustomerInfoForPendingRandomOrders() throws Exception {
|
||||
String marker = "privacy-list-" + LocalDateTime.now().toString();
|
||||
|
||||
Reference in New Issue
Block a user