Jersey 客户端不能使用 JAXB Moxy 序列化 send/receive XML 消息?
Jersey Client can not send/receive XML messages with JAXB Moxy serialization?
我正在尝试使用 jersey-client 发出一些带有 XML 消息的 RESTful 请求。我不想为任何端点提供服务,因此不涉及球衣服务器包。
出于测试目的,我使用可公开访问的 http://www.thomas-bayer.com/sqlrest/CUSTOMER 测试服务。
如 9.2.4. Using Custom JAXBContext 所述,我有一个自定义的 ContextResolver class,它是:
@Provider
@Produces({"application/xml"})
public class MyJaxbContextProvider implements ContextResolver<JAXBContext> {
private JAXBContext context;
public JAXBContext getContext(Class<?> type) {
if (context == null) {
try {
context = JAXBContext.newInstance("resttest.jaxb");
} catch (JAXBException e) {
throw new RuntimeException(e);
}
}
return context;
}
}
此 ContextResolver 已在其余客户端中注册:
client = ClientBuilder.newClient().register(MoxyXmlFeature.class).register(MyJaxbContextProvider.class);
我的客户实体是:
@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "", propOrder = {
"id",
"firstname",
"lastname",
"street",
"city"
})
@XmlRootElement(name = "CUSTOMER")
public class Customer {
@XmlElement(name = "ID")
protected Integer id;
@XmlElement(name = "FIRSTNAME")
protected String firstName;
@XmlElement(name = "LASTNAME")
protected String lastName;
@XmlElement(name = "STREET")
protected String street;
@XmlElement(name = "CITY")
protected String city;
// getters and setters following
// ...
}
最后 class 发出实际请求的测试是:
public class RestClientTest {
private static Client client;
@BeforeClass
public static void beforeClass() {
client = ClientBuilder.newClient().register(MoxyXmlFeature.class).register(MyJaxbContextProvider.class);
}
@Test
public void testCreateCustomerWithEntity() { // Error
Customer customer = new Customer();
customer.setId(50);
customer.setFirstName("Nikol");
Response res = client.target("http://www.thomas-bayer.com/sqlrest/CUSTOMER/").request()
.post(entity(customer, MediaType.APPLICATION_XML_TYPE));
}
@Test
public void testGetCustomer() { // Error
Customer customer = client.target("http://www.thomas-bayer.com/sqlrest/CUSTOMER/3/").request()
.get(new GenericType<Customer>() {});
assertThat(customer.getId(), equalTo(3));
}
}
我已将这些文件打包到 https://github.com/georgeyanev/resttest
的 resttest 项目中
克隆后,可以简单地使用
执行测试
mvn test
我希望当我发出 POST 请求并传递一个 Customer 实例时,后者将由球衣客户端 (testCreateCustomerWithEntity) 编组。
当我发出 GET 请求时,返回的 Customer 实体将被解组 (testGetCustomer)。
但是这两个测试都失败了, MessageBodyProviderNotFoundException 说没有找到媒体类型 application/xml 和类型 Customer.
的 MessageBodyWriter/MessageBodyReader
我在 oracle java 1.8.0_25
中使用 2.19 版本的 jersey-client 和 jersey-media-moxy 库
这可能是什么原因?
似乎需要对 jersey-media-jaxb 的额外依赖才能让 jersey 选择自定义 ContextResolver。然后使用标准 JAXB 机制定义 JAXBContextFactory,从中可以获取 JAXBContext 实例。
在这种情况下,JAXBContextFactory class 在 resttest.jaxb
包中的 jaxb.properties
文件中指定。
我正在尝试使用 jersey-client 发出一些带有 XML 消息的 RESTful 请求。我不想为任何端点提供服务,因此不涉及球衣服务器包。
出于测试目的,我使用可公开访问的 http://www.thomas-bayer.com/sqlrest/CUSTOMER 测试服务。
如 9.2.4. Using Custom JAXBContext 所述,我有一个自定义的 ContextResolver class,它是:
@Provider
@Produces({"application/xml"})
public class MyJaxbContextProvider implements ContextResolver<JAXBContext> {
private JAXBContext context;
public JAXBContext getContext(Class<?> type) {
if (context == null) {
try {
context = JAXBContext.newInstance("resttest.jaxb");
} catch (JAXBException e) {
throw new RuntimeException(e);
}
}
return context;
}
}
此 ContextResolver 已在其余客户端中注册:
client = ClientBuilder.newClient().register(MoxyXmlFeature.class).register(MyJaxbContextProvider.class);
我的客户实体是:
@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "", propOrder = {
"id",
"firstname",
"lastname",
"street",
"city"
})
@XmlRootElement(name = "CUSTOMER")
public class Customer {
@XmlElement(name = "ID")
protected Integer id;
@XmlElement(name = "FIRSTNAME")
protected String firstName;
@XmlElement(name = "LASTNAME")
protected String lastName;
@XmlElement(name = "STREET")
protected String street;
@XmlElement(name = "CITY")
protected String city;
// getters and setters following
// ...
}
最后 class 发出实际请求的测试是:
public class RestClientTest {
private static Client client;
@BeforeClass
public static void beforeClass() {
client = ClientBuilder.newClient().register(MoxyXmlFeature.class).register(MyJaxbContextProvider.class);
}
@Test
public void testCreateCustomerWithEntity() { // Error
Customer customer = new Customer();
customer.setId(50);
customer.setFirstName("Nikol");
Response res = client.target("http://www.thomas-bayer.com/sqlrest/CUSTOMER/").request()
.post(entity(customer, MediaType.APPLICATION_XML_TYPE));
}
@Test
public void testGetCustomer() { // Error
Customer customer = client.target("http://www.thomas-bayer.com/sqlrest/CUSTOMER/3/").request()
.get(new GenericType<Customer>() {});
assertThat(customer.getId(), equalTo(3));
}
}
我已将这些文件打包到 https://github.com/georgeyanev/resttest
的 resttest 项目中
克隆后,可以简单地使用
mvn test
我希望当我发出 POST 请求并传递一个 Customer 实例时,后者将由球衣客户端 (testCreateCustomerWithEntity) 编组。
当我发出 GET 请求时,返回的 Customer 实体将被解组 (testGetCustomer)。
但是这两个测试都失败了, MessageBodyProviderNotFoundException 说没有找到媒体类型 application/xml 和类型 Customer.
我在 oracle java 1.8.0_25
中使用 2.19 版本的 jersey-client 和 jersey-media-moxy 库这可能是什么原因?
似乎需要对 jersey-media-jaxb 的额外依赖才能让 jersey 选择自定义 ContextResolver。然后使用标准 JAXB 机制定义 JAXBContextFactory,从中可以获取 JAXBContext 实例。
在这种情况下,JAXBContextFactory class 在 resttest.jaxb
包中的 jaxb.properties
文件中指定。