0
# Utility Methods and Helper Classes
1
2
This document covers the utility classes and helper methods that simplify creating and manipulating data provider arrays.
3
4
## Required Imports
5
6
```java
7
import com.tngtech.java.junit.dataprovider.DataProviders;
8
import static com.tngtech.java.junit.dataprovider.DataProviders.*;
9
import java.util.List;
10
import java.util.ArrayList;
11
import java.util.Arrays;
12
```
13
14
## DataProviders Utility Class
15
16
The DataProviders class provides static helper methods for creating data provider arrays with less boilerplate code.
17
18
```java { .api }
19
public class DataProviders {
20
21
/**
22
* Create Object array containing all given arguments.
23
* @param args arguments to include in array
24
* @return Object array containing all args
25
*/
26
public static Object[] $(Object... args)
27
28
/**
29
* Create array of Object arrays from given arrays.
30
* @param args Object arrays to combine
31
* @return array of Object arrays
32
*/
33
public static Object[][] $$(Object[]... args)
34
35
/**
36
* Create dataprovider test for each argument.
37
* @param args arguments to wrap individually
38
* @return array containing Object arrays for each single argument
39
*/
40
public static Object[][] testForEach(Object... args)
41
42
/**
43
* Create dataprovider test for each element in Iterable.
44
* @param args Iterable to convert
45
* @return array containing Object arrays for each element
46
* @deprecated since 1.12.0 - Iterable can be returned directly
47
*/
48
@Deprecated
49
public static <T> Object[][] testForEach(Iterable<T> args)
50
51
/**
52
* Create dataprovider test for each enum value.
53
* @param enumClass enum Class to get values from
54
* @return array containing Object arrays for each enum value
55
*/
56
public static <E extends Enum<E>> Object[][] testForEach(Class<E> enumClass)
57
58
/**
59
* Create cross product of two data providers.
60
* @param rows1 first dataprovider data
61
* @param rows2 second dataprovider data
62
* @return cross product combining all row combinations
63
*/
64
public static Object[][] crossProduct(Object[][] rows1, Object[][] rows2)
65
}
66
```
67
68
### Basic Array Creation
69
70
The `$()` and `$$()` methods provide a concise syntax for creating data provider arrays:
71
72
```java
73
import static com.tngtech.java.junit.dataprovider.DataProviders.*;
74
75
@DataProvider
76
public static Object[][] testData() {
77
return $$(
78
$("hello", 5, true),
79
$("world", 5, true),
80
$("", 0, false),
81
$("testing", 7, true)
82
);
83
}
84
85
// Equivalent to:
86
@DataProvider
87
public static Object[][] testDataVerbose() {
88
return new Object[][] {
89
new Object[] { "hello", 5, true },
90
new Object[] { "world", 5, true },
91
new Object[] { "", 0, false },
92
new Object[] { "testing", 7, true }
93
};
94
}
95
```
96
97
### Single Parameter Tests
98
99
Use `testForEach()` when each data item should be a separate test case:
100
101
```java
102
@DataProvider
103
public static Object[][] stringValues() {
104
return testForEach("alpha", "beta", "gamma", "delta");
105
}
106
107
// Equivalent to:
108
// return new Object[][] { {"alpha"}, {"beta"}, {"gamma"}, {"delta"} };
109
110
@Test
111
@UseDataProvider("stringValues")
112
public void testSingleString(String value) {
113
assertNotNull(value);
114
assertTrue(value.length() > 0);
115
}
116
```
117
118
### Enum Testing
119
120
Test all values of an enum easily:
121
122
```java
123
enum Priority { LOW, MEDIUM, HIGH, CRITICAL }
124
125
@DataProvider
126
public static Object[][] allPriorities() {
127
return testForEach(Priority.class);
128
}
129
130
// Equivalent to:
131
// return new Object[][] { {LOW}, {MEDIUM}, {HIGH}, {CRITICAL} };
132
133
@Test
134
@UseDataProvider("allPriorities")
135
public void testPriorityHandling(Priority priority) {
136
assertNotNull(priority);
137
// Test priority-specific logic
138
}
139
```
140
141
### Iterable Conversion (Deprecated)
142
143
While still available, direct Iterable return is now preferred:
144
145
```java
146
// Deprecated approach
147
@DataProvider
148
public static Object[][] fromList() {
149
List<String> items = Arrays.asList("item1", "item2", "item3");
150
return testForEach(items);
151
}
152
153
// Preferred approach (since 1.12.0)
154
@DataProvider
155
public static List<String> fromListDirect() {
156
return Arrays.asList("item1", "item2", "item3");
157
}
158
```
159
160
### Cross Product Combinations
161
162
Generate all combinations of two data sets:
163
164
```java
165
@DataProvider
166
public static Object[][] userTypes() {
167
return $$($("admin"), $("user"), $("guest"));
168
}
169
170
@DataProvider
171
public static Object[][] permissions() {
172
return $$($("read"), $("write"), $("delete"));
173
}
174
175
@DataProvider
176
public static Object[][] userPermissionCombinations() {
177
return crossProduct(userTypes(), permissions());
178
}
179
180
// Results in:
181
// [["admin", "read"], ["admin", "write"], ["admin", "delete"],
182
// ["user", "read"], ["user", "write"], ["user", "delete"],
183
// ["guest", "read"], ["guest", "write"], ["guest", "delete"]]
184
185
@Test
186
@UseDataProvider("userPermissionCombinations")
187
public void testUserPermissions(String userType, String permission) {
188
// Test all user type and permission combinations
189
}
190
```
191
192
## Advanced Utility Patterns
193
194
### Dynamic Data Generation
195
196
Combine utilities with dynamic data generation:
197
198
```java
199
@DataProvider
200
public static Object[][] dynamicRangeData() {
201
List<Object[]> data = new ArrayList<>();
202
for (int i = 1; i <= 5; i++) {
203
data.add($("value" + i, i * 10, i % 2 == 0));
204
}
205
return data.toArray(new Object[0][]);
206
}
207
208
// Or using testForEach with computed values
209
@DataProvider
210
public static Object[][] computedValues() {
211
List<Integer> values = IntStream.range(1, 10)
212
.boxed()
213
.collect(Collectors.toList());
214
return testForEach(values);
215
}
216
```
217
218
### Complex Cross Products
219
220
Generate complex combinations with multiple dimensions:
221
222
```java
223
@DataProvider
224
public static Object[][] browsers() {
225
return testForEach("chrome", "firefox", "safari");
226
}
227
228
@DataProvider
229
public static Object[][] resolutions() {
230
return testForEach("1920x1080", "1366x768", "390x844");
231
}
232
233
@DataProvider
234
public static Object[][] platforms() {
235
return testForEach("windows", "mac", "linux");
236
}
237
238
@DataProvider
239
public static Object[][] allEnvironmentCombinations() {
240
Object[][] browserRes = crossProduct(browsers(), resolutions());
241
return crossProduct(browserRes, platforms());
242
}
243
244
@Test
245
@UseDataProvider("allEnvironmentCombinations")
246
public void testAcrossEnvironments(String browser, String resolution, String platform) {
247
// Test with all browser/resolution/platform combinations
248
}
249
```
250
251
### Filtering and Transforming Data
252
253
Create specialized data sets:
254
255
```java
256
@DataProvider
257
public static Object[][] positiveNumbers() {
258
return testForEach(1, 5, 10, 100, 1000);
259
}
260
261
@DataProvider
262
public static Object[][] negativeNumbers() {
263
return testForEach(-1, -5, -10, -100, -1000);
264
}
265
266
@DataProvider
267
public static Object[][] allNumbers() {
268
return crossProduct(
269
$$($("positive")),
270
positiveNumbers()
271
).concat(crossProduct(
272
$$($("negative")),
273
negativeNumbers()
274
));
275
}
276
277
// Manual concatenation helper
278
private static Object[][] concat(Object[][] array1, Object[][] array2) {
279
Object[][] result = new Object[array1.length + array2.length][];
280
System.arraycopy(array1, 0, result, 0, array1.length);
281
System.arraycopy(array2, 0, result, array1.length, array2.length);
282
return result;
283
}
284
```
285
286
## Integration with External Data
287
288
Combine utilities with external data sources:
289
290
### File-Based Data
291
292
```java
293
@DataProvider
294
public static Object[][] fromCSVFile() throws IOException {
295
List<Object[]> data = new ArrayList<>();
296
try (BufferedReader reader = Files.newBufferedReader(Paths.get("test-data.csv"))) {
297
String line;
298
while ((line = reader.readLine()) != null) {
299
String[] parts = line.split(",");
300
data.add($(parts[0], Integer.parseInt(parts[1]), Boolean.parseBoolean(parts[2])));
301
}
302
}
303
return data.toArray(new Object[0][]);
304
}
305
```
306
307
### Database Data
308
309
```java
310
@DataProvider
311
public static Object[][] fromDatabase() {
312
// Assuming you have a database connection
313
List<Object[]> data = new ArrayList<>();
314
String sql = "SELECT name, age, active FROM test_users";
315
316
try (PreparedStatement stmt = connection.prepareStatement(sql);
317
ResultSet rs = stmt.executeQuery()) {
318
while (rs.next()) {
319
data.add($(rs.getString("name"), rs.getInt("age"), rs.getBoolean("active")));
320
}
321
} catch (SQLException e) {
322
throw new RuntimeException("Failed to load test data", e);
323
}
324
325
return data.toArray(new Object[0][]);
326
}
327
```
328
329
### JSON Data
330
331
```java
332
@DataProvider
333
public static Object[][] fromJSONFile() throws IOException {
334
ObjectMapper mapper = new ObjectMapper();
335
JsonNode root = mapper.readTree(new File("test-data.json"));
336
337
List<Object[]> data = new ArrayList<>();
338
for (JsonNode item : root) {
339
data.add($(
340
item.get("name").asText(),
341
item.get("value").asInt(),
342
item.get("enabled").asBoolean()
343
));
344
}
345
346
return data.toArray(new Object[0][]);
347
}
348
```
349
350
## Performance Considerations
351
352
### Large Data Sets
353
354
For large data sets, consider lazy loading or streaming approaches:
355
356
```java
357
@DataProvider
358
public static Iterator<Object[]> largeDataSet() {
359
return new Iterator<Object[]>() {
360
private int current = 0;
361
private final int max = 100000;
362
363
@Override
364
public boolean hasNext() {
365
return current < max;
366
}
367
368
@Override
369
public Object[] next() {
370
return $("item" + current, current++);
371
}
372
};
373
}
374
```
375
376
### Memory Optimization
377
378
Reuse common data structures:
379
380
```java
381
private static final Object[][] COMMON_STRINGS = testForEach(
382
"alpha", "beta", "gamma", "delta"
383
);
384
385
@DataProvider
386
public static Object[][] reusedData() {
387
return COMMON_STRINGS; // Reuse instead of recreating
388
}
389
```