2016-04-08 11 views
5

У меня есть общий класс ответа обертки:Как определить неподдерживаемый тип поля?

public class Response <T> { 
    T response; 
} 

и несвязанные классы быть обернуто:

public class ServiceResponse { 
    String someField; 
} 

Когда я делаю запрос на обслуживание, я получаю ответ JSON, который выглядит примерно так:

{ "code":200, "response":{"someField":"some text"} } 

Теперь все мои ответы на обслуживание имеют одинаковую внешнюю оболочку, то есть все они имеют:

{ "code":200, "timestamp":"....", "response":... } 

Но фактический формат/тип поля ответа различен для каждого запроса на обслуживание. Когда я преобразовал ответ, мне нужно знать тип response поля, так что я могу создать соответствующий экземпляр, если десериализации были сделаны в Response, я мог бы использовать:

response = new T(jsonParser); 

Однако, я делаю все это внутри библиотеки, которая приводится в движение за счет отражения, так что я обычно десериализации целое дерево с кодом, как:

wrapper = deserializer.parseObject(Response<ServiceResponse>.class) 

, но в этот момент мой метод ParseObject не может правильно определить тип T.

Я могу использовать что-то вроде:

Response<ServiceResponse> response = new Response<>(); 
Field field = response.getClass().getDeclaredField("response"); 
Type type = field.getGenericType(); 

который затем говорит мне, что response имеет тип T но то, что я на самом деле нужно ServiceResponse

Per this SO question Я попытался заброса ParameterizedType, но это было на самом деле, кажется, обратиться к поле типа Response<ServiceResponse>, а не фактическое поле внутри (и это не удается, потому что type не может быть брошена как ParameterizedType)

есть ли способ, чтобы определить (во время выполнения) необработанный тип response?

В конце концов, я могу завершить создание аннотации, в которой более подробно описано, как десериализовать поле, возможно, предоставляя функцию для этого, но предпочитая более прозрачный подход.

Другая возможность может быть на самом деле присвоить пустой экземпляр Т в ответ на время инициализации, а затем я мог захватить фактический тип от этого ...

+0

Короткий ответ: нет. Длинный ответ: укажите более подробную информацию о том, как вы используете 'Response'. Небольшой фрагмент, в котором вы пытаетесь получить «Поле», вводит в заблуждение, потому что нет смысла это делать, вы уже знаете, что у вас есть «ServiceResponse».Как вы получаете свой ответ «»? – Savior

+0

Предоставлено больше информации о прецеденте, но по существу я пытаюсь десериализовать «Response » из запроса сетевой службы. На внешнем уровне я знаю что? есть, но в коде десериализации я этого не делаю, поэтому я пытаюсь восстановить его из доступной информации отражения. –

+0

И, боюсь, ваш короткий ответ, вероятно, является реальным ответом, поскольку дженерики действительно удобная компиляторная фантастика. –

ответ

-1

Заканчивать этот пост: http://mydailyjava.blogspot.com/2013/06/advanced-java-generics-retreiving.html

Это фактически точно что вы ищете.

В соответствии с этим вам просто нужно расширить класс Response, а затем запросить общий тип его супер.

+0

Link-only-ответы обычно нахмурились ... – Marco13

+0

@ Marco13, вы правы, но я не воспользовался удобством, чтобы вырезать и вставить код из сообщения в блоге – Gilad

+0

Конечно (я не сторонник, BTW) , но, возможно, вставить эту ссылку в качестве комментария было бы достаточно ... – Marco13

Смежные вопросы