У меня есть служба REST, построенная с использованием Джерси и развернутая в AppEngine. Служба REST реализует глагол PUT, который потребляет тип приложения /json media. Связывание данных выполняется Jackson.
Глагол использует отношение предприятий-департаментов, представленных в JSON, как
{"name":"myEnterprise", "departments":["HR","IT","SC"]}
На стороне клиента я использую gson для преобразования представления JSON в объект java. Затем я передаю объект в свою службу REST, и он отлично работает.
Проблема:
Когда у моего представления JSON есть только один элемент в коллекции
{"name":"myEnterprise", "departments":["HR"]}
служба не может десериализовать объект.
ATTENTION: /enterprise/enterprise: org.codehaus.jackson.map.JsonMappingException:
Can not deserialize instance of java.util.ArrayList out of VALUE_STRING token at
[Source: [email protected]; line: 1, column: 2
Как сообщают другие пользователи, решение должно добавить флаг ACCEPT_SINGLE_VALUE_AS_ARRAY (например, Джерси: нельзя десериализовать экземпляр ArrayList из строки). Тем не менее, я не контролирую ObjectMapper, потому что на стороне обслуживания он прозрачно сделан Jackson.
Вопрос:
Есть ли способ настроить ObjectMapper на стороне службы, чтобы включить ACCEPT_SINGLE_VALUE_AS_ARRAY? аннотации? web.xml?
Детали кода
Объект Java:
@XmlRootElement
public class Enterprise {
private String name;
private List<String> departments;
public Enterprise() {}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public List<String> getDepartments() {
return departments;
}
public void setDepartments(List<String> departments) {
this.departments = departments;
}
}
Сторона службы REST:
@PUT
@Consumes(MediaType.APPLICATION_JSON)
@Produces(MediaType.APPLICATION_JSON)
@Path("/enterprise")
public Response putEnterprise(Enterprise enterprise,
@Context HttpServletRequest req){
...
}
Клиентская сторона:
...
String jsonString = "{\"name\":\"myEnterprise\", \"departments\":[\"HR\"]}";
Enterprise enterprise = gson.fromJson(jsonString, Enterprise.class);
System.out.println(gson.toJson(enterprise));
response = webResource
.type(MediaType.APPLICATION_JSON)
.put(ClientResponse.class,enterprise);
if (response.getStatus() >= 400) {
throw new RuntimeException("Failed : HTTP error code : " + response.getStatus());
}
...