Как использовать ответ Jax-RS 2.0 от Mule Apikit
Я пытаюсь получить ответ JAX-RS 2 с клиентом Джерси 2.17.
Response response = ClientBuilder.newClient()
.target("http://localhost:8080/api")
.path("organisations")
.request(MediaType.APPLICATION_JSON)
.get(); //[1] .get(GetOrganisationsResponse.class);
//[2] System.out.println("headers=" + response.getHeaders());
//[3] String json = response.readEntity(String.class);
//[4] System.out.println("json=" + json);
Organisations orgs = response.readEntity(Organisations.class);
Ответом служит Муле Апикит.
<flow name="get:/organisations:my-api-config" >
<set-payload value="#[app.registry['organisations'].getOrganisations(message.inboundProperties['start'], message.inboundProperties['pages'])]" doc:name="Set Payload" />
</flow>
POJO генерируются из описания RAML. Вот сгенерированный POJO для вышеуказанного сервиса:
/**
* A collection of organisations
*
*/
@JsonInclude(JsonInclude.Include.NON_NULL)
@Generated("org.jsonschema2pojo")
@JsonPropertyOrder({
"size",
"organisations"
})
public class Organisations {
/**
*
* (Required)
*
*/
@JsonProperty("size")
private Integer size;
@JsonProperty("organisations")
private List<Organisation> organisations = new ArrayList<Organisation>();
@JsonIgnore
private Map<String, Object> additionalProperties = new HashMap<String, Object>();
/**
*
* (Required)
*
* @return
* The size
*/
@JsonProperty("size")
public Integer getSize() {
return size;
}
/**
*
* (Required)
*
* @param size
* The size
*/
@JsonProperty("size")
public void setSize(Integer size) {
this.size = size;
}
public Organisations withSize(Integer size) {
this.size = size;
return this;
}
/**
*
* @return
* The organisations
*/
@JsonProperty("organisations")
public List<Organisation> getOrganisations() {
return organisations;
}
/**
*
* @param organisations
* The organisations
*/
@JsonProperty("organisations")
public void setOrganisations(List<Organisation> organisations) {
this.organisations = organisations;
}
public Organisations withOrganisations(List<Organisation> organisations) {
this.organisations = organisations;
return this;
}
@JsonAnyGetter
public Map<String, Object> getAdditionalProperties() {
return this.additionalProperties;
}
@JsonAnySetter
public void setAdditionalProperty(String name, Object value) {
this.additionalProperties.put(name, value);
}
public Organisations withAdditionalProperty(String name, Object value) {
this.additionalProperties.put(name, value);
return this;
}
}
... и вот сгенерированный GetOrganisationsResponse
за ту же услугу:
public class GetOrganisationsResponse
extends support.ResponseWrapper
{
private GetOrganisationsResponse(Response delegate) {
super(delegate);
}
/**
* OK
*
* @param entity
*
*/
public static Organisations.GetOrganisationsResponse withJsonOK(model.Organisations entity) {
Response.ResponseBuilder responseBuilder = Response.status(200).header("Content-Type", "application/json");
responseBuilder.entity(entity);
return new Organisations.GetOrganisationsResponse(responseBuilder.build());
}
}
В попытке получить экземпляр Organisations
на стороне клиента я заметил следующее:
- Все свойства от
Organisations
в конечном итоге заселены вadditionalProperties
участник, предложивший ни один не был распознан синтаксическим анализатором, - Если я закомментирую элемент AdditionalProperties и получатель / установщик, ошибка парсера будет следующей:
com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException: нераспознанное поле "дата" (модель класса. Организации), не помеченное как игнорируемое (2 известных свойства: "размер", "организации"])
- ... это имеет смысл, если поля даты, заголовков (и других) были сопоставлены не с Ответом, а с Организацией, но почему?
- при раскомментировании строк, отмеченных 2, 3 и 4, ответ, преобразованный в строку, выглядит следующим образом. Не должен
GetOrganisationsResponse
заголовки были проанализированы и возвращены в результатеresponse.getHeaders()
?
заголовки ={X-MULE_ENCODING=[UTF-8], дата = [понедельник, 30 марта 2015 г. 02:16:57 +0000], длина содержимого =[746], X-MULE_SESSION=[...], соединение = [закрыть], http.status=[200], Content-Type=[application/json], Server=[Mule Core/3.6.1]} json={"date":null,"lastModified":null,"headers":{"Content-Type":[" приложения / JSON "]}," субъект ": {" размер ":3," организации ":[{" подъязычная ":"54df33936d725e370b000004","имя":"org1","additionalProperties":{}},{"OID":"54df34406d725e370b000006","название":"org2","additionalProperties":{}},{"OID":"54df33c96d725e370b000005","название":"org3","additionalProperties":{}}],"additionalProperties":{}},"статус":200,"MEDIATYPE": { "Тип": "приложение", "подтип": "JSON", "параметры":{},"wildcardType" ложь "wildcardSubtype" ложь},"allowedMethods":[],"ссылки": [], "печенье":{},"entityTag": нулевой, "StatusInfo":"OK","метаданные": { "Content-Type": [ "приложения / JSON"]},"stringHeaders":{"Content-Type":["приложения / JSON"]}, "длина":-1,"язык": нулевой, "место": нулевой}
- Наконец, при попытке принудительного ответа, генерируемого на стороне сервера с
.get(GetOrganisationsResponse.class)
(uncommenting 1), результат:
Не удается найти десериализатор для неконкретного типа карты [тип карты; класс javax.ws.rs.core.MultivaluedMap, [простой тип, класс java.lang.String] -> [тип коллекции; класс java.util.List, содержит [простой тип, класс java.lang.String]]]
Виновником является следующий код в родительском классе
GetOrganisationResponse
называетсяResponseWrapper
:@Override public MultivaluedMap getHeaders () {return Delegate.getHeaders (); }
@Override public MultivaluedMap getStringHeaders () {return Delegate.getStringHeaders(); }
Спасибо, что указал мне правильное направление:
- Является
client.get()
или жеclient.get(GetOrganisationsResponse.class)
рекомендуемый подход для разбора ответа Mule Apikit на клиенте? (Я не мог найти ответы в документах Mule) - Учитывая, что я получаю ошибки для любого варианта: спасибо за вашу помощь и идеи о том, как их исправить.