package com.tourguide.modules.system.service; import com.tourguide.modules.order.entity.TourOrder; import com.tourguide.modules.system.entity.GuideNotification; import com.tourguide.modules.system.mapper.GuideNotificationMapper; import com.tourguide.modules.system.mapper.GuideNoticeReadMapper; import com.tourguide.modules.system.mapper.SystemNoticeMapper; import com.tourguide.modules.user.service.GuidePushDeviceService; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; import org.mockito.ArgumentCaptor; import java.util.Collections; import static org.assertj.core.api.Assertions.assertThat; import static org.mockito.ArgumentMatchers.any; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; class GuideNotificationServiceTest { private SystemNoticeMapper noticeMapper; private GuideNotificationMapper notificationMapper; private GuidePushDeviceService pushDeviceService; private GuideNotificationService notificationService; @BeforeEach void setUp() { noticeMapper = mock(SystemNoticeMapper.class); notificationMapper = mock(GuideNotificationMapper.class); pushDeviceService = mock(GuidePushDeviceService.class); notificationService = new GuideNotificationService( noticeMapper, mock(GuideNoticeReadMapper.class), notificationMapper, pushDeviceService); } @Test void unreadCountShouldIncludePersonalNotificationsWithoutSystemNotices() { when(noticeMapper.selectList(any())).thenReturn(Collections.emptyList()); when(notificationMapper.selectCount(any())).thenReturn(1L); assertThat(notificationService.unreadCount(8L)).isEqualTo(1L); } @Test void assignedOrderShouldUsePrototypeCopy() { TourOrder order = order(); notificationService.notifyOrderAssigned(order); ArgumentCaptor captor = ArgumentCaptor.forClass(GuideNotification.class); verify(notificationMapper).insert(captor.capture()); GuideNotification notification = captor.getValue(); String content = "您有一个新的讲解订单,请查看"; assertThat(notification.getTitle()).isEqualTo("接单提醒"); assertThat(notification.getContent()).isEqualTo(content); verify(pushDeviceService).push(8L, "接单提醒", content, "/pages/order-detail/index?id=99"); } @Test void visitorCancellationShouldUsePrototypeCopy() { TourOrder order = order(); notificationService.notifyVisitorCancelledOrder(order); verify(pushDeviceService).push(8L, "取消提醒", "您有一个讲解订单被取消,请查看", "/pages/order-detail/index?id=99"); } @Test void reviewedOrderShouldNotifyGuide() { TourOrder order = order(); notificationService.notifyOrderReviewed(order); ArgumentCaptor captor = ArgumentCaptor.forClass(GuideNotification.class); verify(notificationMapper).insert(captor.capture()); GuideNotification notification = captor.getValue(); assertThat(notification.getNotificationType()).isEqualTo("ORDER_REVIEWED"); assertThat(notification.getOrderId()).isEqualTo(99L); assertThat(notification.getTargetUrl()).isEqualTo("/pages/order-detail/index?id=99"); verify(pushDeviceService).push(8L, "评价提醒", "您有一条新的订单评价,请查看", "/pages/order-detail/index?id=99"); } @Test void auditResultShouldUsePrototypeCopy() { notificationService.notifyAuditResult(8L, true); ArgumentCaptor captor = ArgumentCaptor.forClass(GuideNotification.class); verify(notificationMapper).insert(captor.capture()); GuideNotification notification = captor.getValue(); assertThat(notification.getTitle()).isEqualTo("系统提醒"); assertThat(notification.getContent()).isEqualTo("您的资料审核已通过"); } @Test void serviceReminderShouldPointToMeetingPoint() { TourOrder order = order(); notificationService.pushServiceReminder(order); verify(pushDeviceService).push(8L, "请准备前往汇合点", "您的讲解服务即将开始,请提前到达 景区正门。", "/pages/order-detail/index?id=99"); } private TourOrder order() { TourOrder order = new TourOrder(); order.setId(99L); order.setGuideId(8L); order.setScenicName("青城山"); order.setMeetingPointName("景区正门"); order.setPackageName("精品拼团"); order.setPeopleCount(4); return order; } }