Я пытаюсь использовать json, который содержит карту, но ничего не работает. Все, что я получаю, является нулем.
Я пытался использовать методы getForObject (), getForEntity () с типом ответа типизации типа оболочки ConsulServicesResponse.class, но ничего не работает. Использование Object вместо ConsulServicesResponse работает нормально, но я бы предпочел использовать строгую типизацию.
У меня есть такой json, исходящий от моего консула агента api:
{
"synchronizer-1-0": {
"ID": "synchronizer-1-0",
"Service": "synchronizer-1-0",
"Tags": [
"synchronize"
],
"Meta": {},
"Port": 8080,
"Address": "localhost",
"Weights": {
"Passing": 1,
"Warning": 1
},
"EnableTagOverride": false
}
}
как видите, "synchronizer-1-0": {...} это карта. Я создал модель, которую следует использовать при потреблении:
Это оболочка ответа:
@Getter
@Setter
public class ConsulServicesResponse {
@JsonProperty
private String name;
@JsonProperty
private ConsulService services;
}
Это значение POJO:
@NoArgsConstructor
@Getter
@JsonIgnoreProperties(ignoreUnknown = true)
public class ConsulService implements Serializable {
@JsonProperty(value = "ID")
private String id;
@JsonProperty(value = "Service")
private String service;
@JsonProperty(value = "Tags")
private String[] tags;
@JsonProperty(value = "Meta")
private String meta;
@JsonProperty(value = "Port")
private Integer port;
@JsonProperty(value = "Address")
private String address;
@JsonProperty(value = "Weights")
private Weights weights;
@JsonProperty(value = "EnableTagOverride")
private Boolean enableTagOverride;
private class Weights {
@JsonProperty(value = "Passing")
private Integer passing;
@JsonProperty(value = "Warning")
private Integer warning;
}
}
Для правильной сериализации / десериализации я добавляю отображения по умолчанию в мой компонент RestTemplate следующим образом:
@Configuration
public class AppConfiguration {
@Bean
RestTemplate restTemplate(){
RestTemplate restTemplate = new RestTemplate();
restTemplate.getMessageConverters().add(new MappingJackson2HttpMessageConverter());
restTemplate.getMessageConverters().add(new StringHttpMessageConverter());
return restTemplate;
}
@Bean
@Scope("singleton")
ConsulCache consulCache(){
return new ConsulCache();
}
}
И, наконец, в моем контроллере я использую сервис, где я вызываю restTemplate:
@Component
public class ConsulCacheUpdater {
private static final Logger log = LoggerFactory.getLogger(ConsulCacheUpdater.class);
private final String AGENT_PREFIX = "v1/agent/";
private final String CONSUL_SERVICES = "services";
private final String PRETTY_VIEW = "?pretty";
@Autowired
ApplicationContext ctx;
@Autowired
private DiscoveryClient discoveryClient;
@Autowired
Environment environment;
@Autowired
private RestTemplate restTemplate;
@Autowired
private ConsulCache consulCache;
@Scheduled(initialDelay = 3_000, fixedRate = 30_000)
public void updateServiceList(){
String consul_url = String.format("http://%s:%s/%s%s",
environment.getProperty("spring.cloud.consul.host"),
environment.getProperty("spring.cloud.consul.port"),
AGENT_PREFIX,
CONSUL_SERVICES + PRETTY_VIEW);
ResponseEntity<ConsulServicesResponse> response = restTemplate.exchange(
consul_url,
HttpMethod.GET,
null,
ConsulServicesResponse.class);
if (response.getStatusCode().equals(HttpStatus.OK)){
ConsulServicesResponse cs = response.getBody();
}
}
}
Итак, мой CS нулевой. Что я делаю не так?