刘光辉
4 小时以前 06f314545ac3514d7ce28939920866ae8188d31c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
package jnpf.dmsService;
 
import jnpf.base.ActionResult;
import jnpf.base.BillRuleApi;
import jnpf.dmsEntity.fenfa.*;
import jnpf.dmsMapper.DmsWenjianDayinJishuMapper;
import jnpf.exception.DataException;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import java.time.ZoneId;
import java.time.ZonedDateTime;
import java.util.*;
import static org.junit.jupiter.api.Assertions.*;
import static org.mockito.ArgumentMatchers.*;
import static org.mockito.Mockito.*;
 
class DmsWenjianDayinHaomaServiceTest {
    final DmsWenjianDayinJishuMapper mapper = mock(DmsWenjianDayinJishuMapper.class);
    final BillRuleApi bills = mock(BillRuleApi.class);
    final DmsWenjianDayinHaomaService service = new DmsWenjianDayinHaomaService(mapper, bills);
    final DmsWenjianDayinRenwuEntity task = new DmsWenjianDayinRenwuEntity();
    final List<DmsWenjianDayinHaoma> stored = new ArrayList<>();
    @BeforeEach void setup() {
        task.setId("task"); task.setWenjianBianhao("DOC"); task.setBanbenhao("A"); task.setDayinFenshu(5);
        when(mapper.selectTaskNumbers("tenant", "task")).thenAnswer(c -> new ArrayList<>(stored));
        when(mapper.reserve(anyString(), eq("tenant"), eq("DOC"), eq("A"), anyInt(), anyInt())).thenAnswer(c -> {
            DmsWenjianDayinJishu counter = new DmsWenjianDayinJishu();
            counter.setId("counter"); counter.setValue(10 + (Integer)c.getArgument(5)); return counter;
        });
        when(bills.getBillNumber("wenjianDayinLiushuihao")).thenAnswer(c -> ActionResult.success("ok", UUID.randomUUID().toString()));
        when(mapper.insertTaskNumber(eq("tenant"), eq("task"), any())).thenAnswer(c -> {stored.add(c.getArgument(2)); return 1;});
    }
    @Test void creationFixesAllCopiesAndRetryNeverAllocatesAgain() {
        List<DmsWenjianDayinHaoma> first = service.ensureTaskNumbers("tenant", task, 0);
        assertEquals(5, first.size());
        assertEquals(List.of(1,2,3,4,5), first.stream().map(DmsWenjianDayinHaoma::getTaskSequence).toList());
        int year = ZonedDateTime.now(ZoneId.of("Asia/Shanghai")).getYear();
        assertEquals(year + "0011", first.getFirst().getCountSerialNumber());
        assertEquals(first, service.ensureTaskNumbers("tenant", task, 2));
        verify(mapper, times(1)).reserve(anyString(), anyString(), anyString(), anyString(), anyInt(), eq(5));
        verify(bills, times(5)).getBillNumber(anyString());
    }
    @Test void legacyTaskAllocatesOnlyRemainingCopiesWithoutCountingHistory() {
        List<DmsWenjianDayinHaoma> result = service.ensureTaskNumbers("tenant", task, 3);
        assertEquals(List.of(4,5), result.stream().map(DmsWenjianDayinHaoma::getTaskSequence).toList());
        verify(mapper).reserve(anyString(), eq("tenant"), eq("DOC"), eq("A"), anyInt(), eq(2));
        assertEquals(result, service.ensureTaskNumbers("tenant", task, 3));
    }
    @Test void damagedOrChangedTaskDoesNotSilentlyAllocateNewNumbers() {
        service.ensureTaskNumbers("tenant", task, 0);
        stored.remove(2);
        assertThrows(DataException.class, () -> service.ensureTaskNumbers("tenant", task, 0));
        verify(bills, times(5)).getBillNumber(anyString());
    }
    @Test void confirmationRequiresExactNextFixedCopiesAndNeverAllocates() {
        var fixed = service.ensureTaskNumbers("tenant", task, 0);
        clearInvocations(mapper, bills);
        service.requireReservedNumbers("tenant", task, 2, fixed.subList(2,4));
        assertThrows(DataException.class, () -> service.requireReservedNumbers("tenant", task, 2, fixed.subList(3,5)));
        verifyNoInteractions(bills);
        verify(mapper, never()).reserve(anyString(), anyString(), anyString(), anyString(), anyInt(), anyInt());
    }
    @Test void overflowStopsBeforeUniqueBillAllocation() {
        when(mapper.reserve(anyString(), anyString(), anyString(), anyString(), anyInt(), anyInt())).thenReturn(null);
        assertThrows(DataException.class, () -> service.ensureTaskNumbers("tenant", task, 0));
        verifyNoInteractions(bills);
    }
    @Test void invalidConsumedSequenceIsRejected() {
        assertThrows(DataException.class, () -> service.ensureTaskNumbers("tenant", task, 6));
        verifyNoInteractions(mapper, bills);
    }
}