aboutsummaryrefslogtreecommitdiffstats
path: root/src/main/java/junitparams/custom
diff options
context:
space:
mode:
Diffstat (limited to 'src/main/java/junitparams/custom')
-rw-r--r--src/main/java/junitparams/custom/CustomParameters.java25
-rw-r--r--src/main/java/junitparams/custom/FileParametersProvider.java62
-rw-r--r--src/main/java/junitparams/custom/ParametersProvider.java26
-rw-r--r--src/main/java/junitparams/custom/combined/Cartesian.java46
-rw-r--r--src/main/java/junitparams/custom/combined/CombinedParameters.java24
-rw-r--r--src/main/java/junitparams/custom/combined/CombinedParametersProvider.java27
6 files changed, 210 insertions, 0 deletions
diff --git a/src/main/java/junitparams/custom/CustomParameters.java b/src/main/java/junitparams/custom/CustomParameters.java
new file mode 100644
index 0000000..06fd4a4
--- /dev/null
+++ b/src/main/java/junitparams/custom/CustomParameters.java
@@ -0,0 +1,25 @@
+package junitparams.custom;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+
+/**
+ * Tells JUnitParams which {@link ParametersProvider} to use for parameters generation.<br>
+ * Use instead of {@link junitparams.Parameters} annotation.
+ * <p>
+ * Can also be used to create custom annotations.<br>
+ * Check {@link junitparams.FileParameters}, {@link FileParametersProvider} and CustomParametersProviderTest for usage examples.
+ */
+@Retention(RetentionPolicy.RUNTIME)
+@Target({ElementType.METHOD, ElementType.ANNOTATION_TYPE})
+public @interface CustomParameters {
+
+ /**
+ * @return Your custom parameters provider class.
+ */
+ Class<? extends ParametersProvider> provider();
+
+}
diff --git a/src/main/java/junitparams/custom/FileParametersProvider.java b/src/main/java/junitparams/custom/FileParametersProvider.java
new file mode 100644
index 0000000..746fe5c
--- /dev/null
+++ b/src/main/java/junitparams/custom/FileParametersProvider.java
@@ -0,0 +1,62 @@
+package junitparams.custom;
+
+import java.io.FileInputStream;
+import java.io.FileReader;
+import java.io.IOException;
+import java.io.InputStreamReader;
+import java.io.Reader;
+
+import junitparams.FileParameters;
+import junitparams.mappers.DataMapper;
+
+public class FileParametersProvider implements ParametersProvider<FileParameters> {
+
+ private FileParameters fileParameters;
+
+ @Override
+ public void initialize(FileParameters fileParameters) {
+ this.fileParameters = fileParameters;
+ }
+
+ @Override
+ public Object[] getParameters() {
+ return paramsFromFile();
+ }
+
+ private Object[] paramsFromFile() {
+ try {
+ Reader reader = createProperReader();
+ DataMapper mapper = fileParameters.mapper().newInstance();
+ try {
+ return mapper.map(reader);
+ } finally {
+ reader.close();
+ }
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new RuntimeException(
+ "Could not successfully read parameters from file: " + fileParameters.value(), e);
+ }
+ }
+
+ private Reader createProperReader() throws IOException {
+ String filepath = fileParameters.value();
+ String encoding = fileParameters.encoding();
+
+ if (filepath.indexOf(':') < 0) {
+ return new FileReader(filepath);
+ }
+
+ String protocol = filepath.substring(0, filepath.indexOf(':'));
+ String filename = filepath.substring(filepath.indexOf(':') + 1);
+
+ if ("classpath".equals(protocol)) {
+ return new InputStreamReader(getClass().getClassLoader().getResourceAsStream(filename), encoding);
+ } else if ("file".equals(protocol)) {
+ return new InputStreamReader(new FileInputStream(filename), encoding);
+ }
+
+ throw new IllegalArgumentException("Unknown file access protocol. Only 'file' and 'classpath' are supported!");
+ }
+
+}
diff --git a/src/main/java/junitparams/custom/ParametersProvider.java b/src/main/java/junitparams/custom/ParametersProvider.java
new file mode 100644
index 0000000..8cf3621
--- /dev/null
+++ b/src/main/java/junitparams/custom/ParametersProvider.java
@@ -0,0 +1,26 @@
+package junitparams.custom;
+
+import java.lang.annotation.Annotation;
+
+/**
+ * An interface for custom parameters providers. To be used with {@link CustomParameters} annotation.
+ * Must have a default no-args constructor.
+ *
+ * @param <A> type of annotation mentioning this provider
+ */
+public interface ParametersProvider<A extends Annotation> {
+
+ /**
+ * Initializes this provider - you can read your custom annotation config here.
+ *
+ * @param parametersAnnotation parameters annotation on test method
+ */
+ void initialize(A parametersAnnotation);
+
+ /**
+ * Actual parameters generation
+ *
+ * @return parameters for test method calls
+ */
+ Object[] getParameters();
+}
diff --git a/src/main/java/junitparams/custom/combined/Cartesian.java b/src/main/java/junitparams/custom/combined/Cartesian.java
new file mode 100644
index 0000000..f98948f
--- /dev/null
+++ b/src/main/java/junitparams/custom/combined/Cartesian.java
@@ -0,0 +1,46 @@
+package junitparams.custom.combined;
+
+import java.util.Arrays;
+import java.util.List;
+
+class Cartesian {
+
+ static Object[] getCartesianProductOf(List<Object[]> array) {
+ if (array == null || array.size() == 0) {
+ return new Object[]{};
+ }
+
+ for (int i = 0; i < array.size() - 1; i++) {
+ Object[] arrayOne = array.get(i);
+ Object[] arrayTwo = array.get(i + 1);
+ array.set(i + 1, cartesianProduct(arrayOne, arrayTwo));
+ }
+
+ return array.get(array.size() - 1);
+ }
+
+ private static Object[] cartesianProduct(Object[] arrayOne, Object[] arrayTwo) {
+ int numberOfCombinations = arrayOne.length * arrayTwo.length;
+ Object[] resultArray = new Object[numberOfCombinations][2];
+
+ int i = 0;
+ for (Object firstElement : arrayOne) {
+ for (Object secondElement : arrayTwo) {
+ resultArray[i] = getCartesianOfTwoElements(firstElement, secondElement);
+ i++;
+ }
+ }
+
+ return resultArray;
+ }
+
+ private static Object getCartesianOfTwoElements(Object objectOne, Object objectTwo) {
+ if (!objectOne.getClass().isArray()) {
+ return new Object[]{objectOne, objectTwo};
+ }
+ Object[] initialArray = (Object[]) objectOne;
+ Object[] newArray = Arrays.copyOf(initialArray, initialArray.length + 1);
+ newArray[newArray.length - 1] = objectTwo;
+ return newArray;
+ }
+}
diff --git a/src/main/java/junitparams/custom/combined/CombinedParameters.java b/src/main/java/junitparams/custom/combined/CombinedParameters.java
new file mode 100644
index 0000000..95e4a5e
--- /dev/null
+++ b/src/main/java/junitparams/custom/combined/CombinedParameters.java
@@ -0,0 +1,24 @@
+package junitparams.custom.combined;
+
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+
+import junitparams.custom.CustomParameters;
+
+@Retention(RetentionPolicy.RUNTIME)
+@CustomParameters(provider = CombinedParametersProvider.class)
+public @interface CombinedParameters {
+ /**
+ * Parameter values defined as a String array.
+ * Each of the elements is a list of values that should be tested for parameters.
+ * Using this annotation will result in creating a n-fold cartesian product of parameter values effectively testing
+ * each possible combination.
+ * Values in the array must match the test method's parameters in order and type.
+ * <p>
+ * Example:<br>
+ * <code>@CombinedParameters({"han,chewie","33,204"})<br>
+ * public void shouldTestAllNameAgeCombinations(String name, Integer age)
+ * </code>
+ */
+ String[] value() default {};
+}
diff --git a/src/main/java/junitparams/custom/combined/CombinedParametersProvider.java b/src/main/java/junitparams/custom/combined/CombinedParametersProvider.java
new file mode 100644
index 0000000..382b6ce
--- /dev/null
+++ b/src/main/java/junitparams/custom/combined/CombinedParametersProvider.java
@@ -0,0 +1,27 @@
+package junitparams.custom.combined;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import junitparams.custom.ParametersProvider;
+import junitparams.internal.Utils;
+
+public class CombinedParametersProvider implements ParametersProvider<CombinedParameters> {
+
+ private CombinedParameters combinedParameters;
+
+ @Override
+ public void initialize(CombinedParameters parametersAnnotation) {
+ this.combinedParameters = parametersAnnotation;
+ }
+
+ @Override
+ public Object[] getParameters() {
+ List<Object[]> list = new ArrayList<Object[]>();
+ for(String parameterArray : combinedParameters.value()) {
+ list.add(Utils.splitAtCommaOrPipe(parameterArray));
+ }
+
+ return Cartesian.getCartesianProductOf(list);
+ }
+}