0

Can someone please tell me whether there is a way to pass the generic type T to getAPIResponse(...) and build the TypeReference within getAPIResponse method.

I would like to pass Model as a generic type to getAPIResponse and have TypeReference built in within the getAPIResponse method.

TypeReference<APIResponse<Model>> type = new TypeReference<APIResponse<Model>>(){};
APIResponse<Model> response = getAPIResponse(result, type);

I would like to avoid building the TypeReference instance outside the getAPIResponse method, rather would like to create the instance within the getAPIResponse method and pass only the Generic type into the method.

getAPIResponse method

protected final <T> APIResponse<T> getAPIResponse(MvcResult pResult, TypeReference<APIResponse<T>> type) {

    APIResponse<T> res = null;
    try {
        res = new ObjectMapper().readValue(pResult.getResponse().getContentAsString(), type);
    }
    catch (IOException e) {
        Assert.fail(ExceptionUtils.getStackTrace(e));
    }

    return res;
}

I tried changing to the below

protected final <T> APIResponse<T> getAPIResponse(MvcResult pResult, T t) {

    APIResponse<T> res = null;
    try {
        TypeReference<APIResponse<T>> type = new TypeReference<APIResponse<T>>(){};
        res = new ObjectMapper().readValue(pResult.getResponse().getContentAsString(), type);
    }
    catch (IOException e) {
        Assert.fail(ExceptionUtils.getStackTrace(e));
    }

    return res;
}

But not I am not sure how to call into this method. Lets say I want to return

 APIResponse<Bank>
 APIResponse<Branch>
 APIResponse<List<Employee>>

How do I pass these generic types into my method call in the invoking class?

serah
  • 2,057
  • 7
  • 36
  • 56
  • For Bank and Brank you can just call it with Bank.class right? But List shows you the reason why TypeReference exists and why it will probably not be possible to work arround this. – Bob Brinks Sep 06 '16 at 13:16
  • @Bob Brinks will http://stackoverflow.com/questions/1079279/class-object-of-generic-class-java work? –  Sep 06 '16 at 13:21
  • __"...whether there is a way to pass the generic type T..."_, yes, that is exactly what the type reference is for. – Jorn Vernee Sep 06 '16 at 13:23
  • @Arkadiy Maybe haven't tried that but you will lose some type safety if you use that and i wouldn't recommend that. – Bob Brinks Sep 06 '16 at 14:15

1 Answers1

-1

UPDATE: It doesn't work. JSON is converted to Map instead of APIResponse, .... :(

Try this:

protected final <T> APIResponse<T> getAPIResponse(MvcResult pResult) {
APIResponse<T> res = null;
    try {
        TypeReference<APIResponse<T>> type = new TypeReference<APIResponse<T>>(){};
        res = new ObjectMapper().readValue(pResult.getResponse().getContentAsString(), type);
    }
    catch (IOException e) {
        Assert.fail(ExceptionUtils.getStackTrace(e));
    }

    return res;
}

And call:

APIResponse<Model> response = getAPIResponse(result);

You don't need give 't' object.

Robertiano
  • 352
  • 1
  • 6
  • 1
    This definitely won't work. You're giving a type variable to the `TypeReference`, not a concrete type. – Sotirios Delimanolis Sep 06 '16 at 13:23
  • 1
    Thanks Robertiano, removed T as a method parameter and works fine. – serah Sep 06 '16 at 13:23
  • @SotiriosDelimanolis - Can you elaborate why it wont work. Seems to work for me with List – serah Sep 06 '16 at 13:24
  • 2
    The type returned by the type reference will be `APIResponse`, as opposed to the actual type `APIResponse`. The `ObjectMapper` can not do anything with that. – Jorn Vernee Sep 06 '16 at 13:26
  • @BobBrinks T could be anything, List, Set>, ... T has no bounders. – Robertiano Sep 06 '16 at 13:33
  • Apologies for jumping to a conclusion very early. I guess I now see the issue. Though my IDE does not throw any parametrization errors and my Junit is able to get an object from the response, it isnt what I expect. When i check the Bank object, the returned value comes as a LinkedList of all the fields in the Bank object , when I try to retrieve the Bank object. I would need to pass the TypeReference. So must I conclude that there is no way for me to build TypeReference inside the getResponseAPI method (..) ? – serah Sep 06 '16 at 13:38