1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.kuali.student.enrollment.class2.courseoffering.service.impl;
18
19 import org.apache.commons.lang.StringUtils;
20 import org.junit.Test;
21 import org.junit.runner.RunWith;
22 import org.kuali.student.enrollment.class2.courseoffering.service.CourseOfferingCodeGenerator;
23 import org.kuali.student.enrollment.courseoffering.dto.ActivityOfferingInfo;
24 import org.kuali.student.enrollment.courseoffering.dto.CourseOfferingInfo;
25 import org.springframework.test.context.ContextConfiguration;
26 import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
27
28 import javax.annotation.Resource;
29 import java.util.ArrayList;
30 import java.util.Collections;
31 import java.util.HashMap;
32 import java.util.List;
33 import java.util.Map;
34 import java.util.concurrent.Callable;
35 import java.util.concurrent.ExecutionException;
36 import java.util.concurrent.ExecutorService;
37 import java.util.concurrent.Executors;
38 import java.util.concurrent.Future;
39
40 import static org.junit.Assert.assertEquals;
41 import static org.junit.Assert.assertTrue;
42
43
44
45
46
47
48 @RunWith(SpringJUnit4ClassRunner.class)
49 @ContextConfiguration(locations = {"classpath:co-test-context.xml"})
50 public class TestCourseOfferingCodeGeneratorImpl {
51
52 @Resource
53 CourseOfferingCodeGenerator offeringCodeGenerator;
54
55
56 private Map<String, Object> _makeDefaultMap(String coCode, List<String> aoCodes){
57 Map<String, Object> mRet = new HashMap<String,Object>();
58
59 mRet.put(CourseOfferingCodeGenerator.COURSE_OFFERING_CODE_KEY, coCode);
60 mRet.put(CourseOfferingCodeGenerator.ACTIVITY_OFFERING_CODE_LIST_KEY, aoCodes);
61 return mRet;
62 }
63
64 @Test
65 public void testGenerator(){
66
67 String code;
68 String courseOfferingCode = "ENGL101";
69 code = offeringCodeGenerator.generateActivityOfferingCode(_makeDefaultMap(courseOfferingCode, new ArrayList<String>()));
70 assertEquals("A",code);
71
72 List<String> aos = new ArrayList<String>();
73 for(char c='A';c<='Z';c++){
74
75 aos.add(String.valueOf(c));
76 }
77
78 Map<String, Object> propMap = _makeDefaultMap(courseOfferingCode, aos);
79 code = offeringCodeGenerator.generateActivityOfferingCode(propMap);
80 assertEquals("AA",code);
81
82 aos.remove(3);
83
84 code = offeringCodeGenerator.generateActivityOfferingCode(propMap);
85 assertEquals("D",code);
86
87 }
88
89 @Test
90 public void testGetNextCode(){
91
92 CourseOfferingCodeGeneratorDBImpl dbImpl = (CourseOfferingCodeGeneratorDBImpl)offeringCodeGenerator;
93
94 assertEquals("A",dbImpl.getNextCode(""));
95 assertEquals("E",dbImpl.getNextCode("D"));
96 assertEquals("AA",dbImpl.getNextCode("Z"));
97 assertEquals("AF",dbImpl.getNextCode("AE"));
98 assertEquals("BA",dbImpl.getNextCode("AZ"));
99 assertEquals("BF",dbImpl.getNextCode("BE"));
100 assertEquals("ZB",dbImpl.getNextCode("ZA"));
101 assertEquals("AAA", dbImpl.getNextCode("ZZ"));
102 assertEquals("AAF",dbImpl.getNextCode("AAE"));
103 assertEquals("ABA",dbImpl.getNextCode("AAZ"));
104 assertEquals("ABG",dbImpl.getNextCode("ABF"));
105 assertEquals("AAAA",dbImpl.getNextCode("ZZZ"));
106 assertEquals("AAEB",dbImpl.getNextCode("AAEA"));
107 assertEquals("AAZB",dbImpl.getNextCode("AAZA"));
108 assertEquals("ABAA",dbImpl.getNextCode("AAZZ"));
109 assertEquals("AZAC",dbImpl.getNextCode("AZAB"));
110 assertEquals("ZZZD",dbImpl.getNextCode("ZZZC"));
111 assertEquals("AAAAA",dbImpl.getNextCode("ZZZZ"));
112 }
113
114 @Test
115 public void testGenerateCourseOfferingInternalCode(){
116
117 String code;
118 code = offeringCodeGenerator.generateCourseOfferingInternalCode(new ArrayList<CourseOfferingInfo>());
119 assertEquals("A",code);
120
121 List<CourseOfferingInfo> cos = new ArrayList<CourseOfferingInfo>();
122 for(char c='A';c<='Z';c++){
123 CourseOfferingInfo a = new CourseOfferingInfo();
124 a.setCourseNumberSuffix(String.valueOf(c));
125
126 cos.add(a);
127 }
128 code = offeringCodeGenerator.generateCourseOfferingInternalCode(cos);
129 assertEquals("AA",code);
130
131 cos.remove(3);
132
133 code = offeringCodeGenerator.generateCourseOfferingInternalCode(cos);
134 assertEquals("D",code);
135 }
136
137 protected List<String> _getBaseAOListNew(){
138 List<String> l = new ArrayList<String>();
139 l.add("A");
140 l.add("B");
141 l.add("C");
142 return l;
143 }
144
145 protected List<ActivityOfferingInfo> _getBaseAOList(){
146 List<ActivityOfferingInfo> aoList = new ArrayList<ActivityOfferingInfo>();
147
148 String courseOfferingCode = "ENGL102";
149
150 ActivityOfferingInfo ao1 = new ActivityOfferingInfo();
151 ao1.setActivityCode("A");
152 ao1.setCourseOfferingCode(courseOfferingCode);
153 aoList.add(ao1);
154
155 ActivityOfferingInfo ao2 = new ActivityOfferingInfo();
156 ao2.setActivityCode("B");
157 ao2.setCourseOfferingCode(courseOfferingCode);
158 aoList.add(ao2);
159
160 ActivityOfferingInfo ao3 = new ActivityOfferingInfo();
161 ao3.setActivityCode("C");
162 ao3.setCourseOfferingCode(courseOfferingCode);
163 aoList.add(ao3);
164
165
166 return aoList;
167 }
168
169
170 @Test
171 public void testGenerateActivityOfferingCode(){
172
173 String courseOfferingCode = "ENGL103";
174
175 List<String> aoList = _getBaseAOListNew();
176 Map<String, Object> propMap = _makeDefaultMap(courseOfferingCode, aoList);
177
178 String nextCode = offeringCodeGenerator.generateActivityOfferingCode(propMap);
179
180
181 assertTrue("D".equals(nextCode));
182
183
184
185 aoList.add("E");
186
187 nextCode = offeringCodeGenerator.generateActivityOfferingCode(propMap);
188
189
190 assertTrue ("D".equals(nextCode));
191
192 }
193
194
195
196
197
198
199 @Test
200 public void testGenerateActivityOfferingCodeMultiThread(){
201 try{
202 test("ENGL104", 6);
203 }catch (Exception ex){
204 ex.printStackTrace();
205 }
206 }
207
208 private void test(final String courseOfferingCode, final int threadCount) throws InterruptedException, ExecutionException {
209
210
211 Callable<String> task = new Callable<String>() {
212
213 @Override
214
215 public String call() {
216
217 return offeringCodeGenerator.generateActivityOfferingCode(_makeDefaultMap(courseOfferingCode, new ArrayList <String>()));
218
219 }
220
221 };
222
223 List<Callable<String>> tasks = Collections.nCopies(threadCount, task);
224
225 ExecutorService executorService = Executors.newFixedThreadPool(threadCount);
226
227 List<Future<String>> futures = executorService.invokeAll(tasks);
228
229 List<String> resultList = new ArrayList<String>(futures.size());
230
231
232
233 for (Future<String> future : futures) {
234
235
236
237 resultList.add(future.get());
238
239 }
240
241
242
243 assert (futures.size() == threadCount);
244
245 List<String> expectedList = new ArrayList<String>(threadCount);
246
247 String nextCode = "";
248 for (long i = 1; i <= threadCount; i++) {
249 nextCode = getNextCode(nextCode);
250 expectedList.add(nextCode);
251
252 }
253
254 Collections.sort(resultList);
255
256 System.out.println("Expected/Got: \n" + expectedList + "\n" + resultList);
257
258 for(int i=0;i< resultList.size(); i++){
259 assertTrue("\nWas expecting \n[" + expectedList.get(i) + "] but got \n[" + resultList.get(i) + "]\n" , expectedList.get(i).equals(resultList.get(i)));
260 }
261
262 }
263
264 public String getNextCode(String source){
265 if (StringUtils.isEmpty(source)){
266 return "A";
267 } else if (StringUtils.endsWithIgnoreCase(source,"Z")){
268 return getNextCode(StringUtils.substringBeforeLast(source,"Z")) + "A";
269 } else {
270 char lastLetter = source.charAt(source.length()-1);
271 return StringUtils.substringBeforeLast(source,""+lastLetter) + ++lastLetter;
272 }
273 }
274
275 }