forked from baidu/uid-generator
-
Notifications
You must be signed in to change notification settings - Fork 0
/
CachedUidGeneratorTest.java
129 lines (108 loc) · 3.65 KB
/
CachedUidGeneratorTest.java
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
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
package com.baidu.fsg.uid;
import com.baidu.fsg.uid.impl.CachedUidGenerator;
import org.apache.commons.lang.StringUtils;
import org.junit.Assert;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import javax.annotation.Resource;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.concurrent.ConcurrentSkipListSet;
import java.util.concurrent.atomic.AtomicInteger;
/**
* Test for {@link CachedUidGenerator}
*
* @author yutianbao
*/
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = { "classpath:uid/cached-uid-spring.xml" })
public class CachedUidGeneratorTest {
private static final int SIZE = 7000000; // 700w
private static final boolean VERBOSE = false;
private static final int THREADS = Runtime.getRuntime().availableProcessors() << 1;
@Resource
private UidGenerator uidGenerator;
/**
* Test for serially generate
*
* @throws IOException
*/
@Test
public void testSerialGenerate() throws IOException {
// Generate UID serially
Set<Long> uidSet = new HashSet<>(SIZE);
for (int i = 0; i < SIZE; i++) {
doGenerate(uidSet, i);
}
// Check UIDs are all unique
checkUniqueID(uidSet);
}
/**
* Test for parallel generate
*
* @throws InterruptedException
* @throws IOException
*/
@Test
public void testParallelGenerate() throws InterruptedException, IOException {
AtomicInteger control = new AtomicInteger(-1);
Set<Long> uidSet = new ConcurrentSkipListSet<>();
// Initialize threads
List<Thread> threadList = new ArrayList<>(THREADS);
for (int i = 0; i < THREADS; i++) {
Thread thread = new Thread(() -> workerRun(uidSet, control));
thread.setName("UID-generator-" + i);
threadList.add(thread);
thread.start();
}
// Wait for worker done
for (Thread thread : threadList) {
thread.join();
}
// Check generate 700w times
Assert.assertEquals(SIZE, control.get());
// Check UIDs are all unique
checkUniqueID(uidSet);
}
/**
* Woker run
*/
private void workerRun(Set<Long> uidSet, AtomicInteger control) {
for (;;) {
int myPosition = control.updateAndGet(old -> (old == SIZE ? SIZE : old + 1));
if (myPosition == SIZE) {
return;
}
doGenerate(uidSet, myPosition);
}
}
/**
* Do generating
*/
private void doGenerate(Set<Long> uidSet, int index) {
long uid = uidGenerator.getUID();
String parsedInfo = uidGenerator.parseUID(uid);
boolean existed = !uidSet.add(uid);
if (existed) {
System.out.println("Found duplicate UID " + uid);
}
// Check UID is positive, and can be parsed
Assert.assertTrue(uid > 0L);
Assert.assertTrue(StringUtils.isNotBlank(parsedInfo));
if (VERBOSE) {
System.out.println(Thread.currentThread().getName() + " No." + index + " >>> " + parsedInfo);
}
}
/**
* Check UIDs are all unique
*/
private void checkUniqueID(Set<Long> uidSet) throws IOException {
System.out.println(uidSet.size());
Assert.assertEquals(SIZE, uidSet.size());
}
}