简体   繁体   中英

DataProvider returning Object[][] does not match argument type

I have a TestNG dataProvider that needs to return an Object[][]. Here is how I get this object array I am returning.

The test method looks like this:

public void testUser(UserModel testData)
  1. Get the parent "Test" method's argument type. (Method m.getParameterTypes()[0].newInstance) and add this to an Object array. (It will add UserModel object type to that array) - This works fine.

  2. Pass this Object[] into a method that reads from a json file and builds it into the object type. Then this method returns an array of objects (Object[]) of that object type based on the json file. - This works fine.

  3. From there I convert the Object[] returned into a 2D object array. It looks like this: Object[size][1]. - It builds the object[][] fine, but the objects may lose their type here.

For example: the array is made up of two objects. it will look like this. Object[1][1] = Object[0] Object[2][1] = Object[1]

  1. I then return this object to be used and it throws the following exception:

    java.lang.IllegalArgumentException: argument type mismatch

I have tried to return the single Object[] that the method returns as the following:

return new Object[][] { singleObjectArray };

But this just ignores the test cases because it's not returning it properly.

How can I make sure that the object array is returning the correct types. I just want to be able to handle arrays of objects from json and have the test case run that many times.

Here is the DataProvider code.

   @DataProvider(name = "DataProviderArray")
protected static Object[][] getCoreDataProviderArray(Method superMethod,
                                                  ITestContext context) {
    List<Object> objectList = new ArrayList<>();

    try {
        objectList.add(superMethod.getParameterTypes()[0].newInstance());

        Object[] objectArray = objectList.toArray();
        JsonUtils jsonUtils = new JsonUtils(TEST_DATA_LOCATION
                + context.getName() + JSON_EXTENSION);

        Object[] newUsers = jsonUtils.createArrayOfObjectsFromJsonFile(objectArray);

        Object [][] objects = new Object[newUsers.length][1];

        for (int i = 0; i < newUsers.length; i++) {
            System.arraycopy(newUsers, i, objects[i], 0, 1);
        }

        return objects;

    } catch (Exception e) {
        throw new RuntimeInterruptionException("Could not return object for "
                + superMethod.getParameterTypes()[0] + "...");
    }
}

and JsonUtils class:

    public Object[] createArrayOfObjectsFromJsonFile(Object[] objectToCreate) {
    gson = new GsonBuilder().create();
    return gson.fromJson(reader, objectToCreate.getClass());

}

and here is the stack trace:

java.lang.IllegalArgumentException: argument type mismatch

at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:497)
at org.testng.internal.MethodInvocationHelper.invokeMethod(MethodInvocationHelper.java:86)
at org.testng.internal.Invoker.invokeMethod(Invoker.java:643)
at org.testng.internal.Invoker.invokeTestMethod(Invoker.java:820)
at org.testng.internal.Invoker.invokeTestMethods(Invoker.java:1128)
at org.testng.internal.TestMethodWorker.invokeTestMethods(TestMethodWorker.java:129)
at org.testng.internal.TestMethodWorker.run(TestMethodWorker.java:112)
at org.testng.TestRunner.privateRun(TestRunner.java:782)
at org.testng.TestRunner.run(TestRunner.java:632)
at org.testng.SuiteRunner.runTest(SuiteRunner.java:366)
at org.testng.SuiteRunner.runSequentially(SuiteRunner.java:361)
at org.testng.SuiteRunner.privateRun(SuiteRunner.java:319)
at org.testng.SuiteRunner.run(SuiteRunner.java:268)
at org.testng.SuiteRunnerWorker.runSuite(SuiteRunnerWorker.java:52)
at org.testng.SuiteRunnerWorker.run(SuiteRunnerWorker.java:86)
at org.testng.TestNG.runSuitesSequentially(TestNG.java:1244)
at org.testng.TestNG.runSuitesLocally(TestNG.java:1169)
at org.testng.TestNG.run(TestNG.java:1064)
at org.testng.IDEARemoteTestNG.run(IDEARemoteTestNG.java:72)
at org.testng.RemoteTestNGStarter.main(RemoteTestNGStarter.java:124)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:497)
at com.intellij.rt.execution.application.AppMain.main(AppMain.java:147)

Thanks in advance!

You should try something like:

@DataProvider(name = "DataProviderArray")
protected static Iterator<Object[]> getCoreDataProviderArray(Method superMethod, ITestContext context) {

  Class<?> type = superMethod.getParameterTypes()[0];     
  JsonUtils jsonUtils = new JsonUtils(TEST_DATA_LOCATION
    + context.getName() + JSON_EXTENSION);  
  List<Object> newUsers;
  try {
    newUsers = jsonUtils.createObjectsFromJsonFile(type);
  } catch (Exception e) {
    throw new RuntimeInterruptionException("Could not return object for "
                + superMethod.getParameterTypes()[0] + "...");
  }

  List<Object[]> objects = new ArrayList<>();
  for (Object user : newUsers) {
    objects.add(new Object[]{user});
  }
  return objects.iterator();
}

Then, the harder part will be JsonUtils with something like:

public List<Object> createObjectsFromJsonFile(Class<?> objectToCreate) {
  gson = new GsonBuilder().create();
  return gson.fromJson(reader, /*<appropriate type array from objectToCreate>*/);
}

But the answer is somewhere here: Java Type Generic as Argument for GSON

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM