- android - 多次调用 OnPrimaryClipChangedListener
- android - 无法更新 RecyclerView 中的 TextView 字段
- android.database.CursorIndexOutOfBoundsException : Index 0 requested, 光标大小为 0
- android - 使用 AppCompat 时,我们是否需要明确指定其 UI 组件(Spinner、EditText)颜色
我正在尝试让 Jersey 支持 GSON,为此我读到我需要实现自定义 MessageBodyWriter 和 MessageBodyReader。
现在我的问题是我找不到这两个接口(interface)的任何明确定义。
来自文档:
public interface MessageBodyWriter<T>
Contract for a provider that supports the conversion of a Java type to a stream. To add a MessageBodyWriter implementation, annotate the implementation class with @Provider. A MessageBodyWriter implementation may be annotated with Produces to restrict the media types for which it will be considered suitable.
和
public interface MessageBodyReader<T>
Contract for a provider that supports the conversion of a stream to a Java type. A MessageBodyReader implementation may be annotated with Consumes to restrict the media types for which it will be considered suitable. Providers implementing MessageBodyReader contract must be either programmatically registered in a JAX-RS runtime or must be annotated with @Provider annotation to be automatically discovered by the JAX-RS runtime during a provider scanning phase.
谁能给我解释一下具体是什么意思吗?
为什么我需要在 GSON 支持的情况下实现它们?
谢谢。
最佳答案
仅指接口(interface)公开的方法的集合。如果我们实现接口(interface),我们必须实现一组契约方法,框架将使用这些方法来利用我们的实现
MessageBodyWriter
- 支持将 Java 类型转换为流的提供者的合约 - 从我们的 JAX-RS 资源方法中,我们返回带有实体主体(它是 Java 对象)或 Java 对象的 Response
。消息正文编写器负责将此 Java 对象转换为响应的输出流。例如(仅供玩耍,假设我们尚未支持 JAXB 编码)
@Override
public void writeTo(Customer c, Class<Customer> type,
Type genericType, Annotation[] annotations,
MediaType mediaType,
MultivaluedMap<String,Object> httpHeaders,
OutputStream entityStream) {
JAXBContext context = JAXBContext.newInstance(type);
Marshaller marsaller = context.createMarshaller();
marshaller.marshal(c, entityStream);
}
您可以看到我创建了 Marshaller
,它将 Customer
对象编码到(由框架)提供的 OutputStream
MessageBodyReader
- 支持将流转换为 Java 类型的提供者的契约(Contract) - 与编写器相同,但这次过程相反。在将 Java 类型传递给我们的 JAX-RS 资源方法之前,需要对其进行转换。例如
@Override
public Customer readFrom(Class<T> type, Type genericType,
Annotation[] annotations, MediaType mediaType,
MultivaluedMap<String,String> httpHeaders,
InputStream entityStream) throws IOException,
WebApplicationException {
JAXBContext context = JAXBContext.newInstance(Customer.class);
Unmarshaller unmarshaller = context.createUnmarshaller();
return (Customer)unarshaller.unmarshal(entityStream);
}
To add a
MessageBodyWriter
implementation, annotate the implementation class with@Provider
. AMessageBodyWriter
implementation may be annotated withProduces
to restrict the media types for which it will be considered suitable
JAX-RS 具有“提供者”的概念。您可以将其视为组件的另一个词。当我们使用 @Provider
注释 JAX-RS 实现的类时,它就可以成为由框架管理的组件。
对于MessageBodyWriters/MessageBodyReaders
,有一个特定的算法来确定每个请求/响应将使用哪个写入器/读取器。基本上发生的事情是 JAX-RS 根据 @Produces
注释匹配来计算列表或编写器。例如,如果我们的资源方法或资源类用 @Produces(MediaType.APPLICATION_XML)
进行注释,并且我们的提供者(编写器)也用此注释,那么我们的编写器将被放入此列表中。然后通过某种算法对这些提供者进行排序。最后,每个写入器都会调用 isWritable
方法,直到其中一个写入器返回 true
为止。这就是将要使用的作家。例如
@Provider
@Produces(MediaType.APPLICATION_XML)
public class MyJAXBMessageBodyWriter
implements MessaheBodyWriter<Customer> {
@Override
public boolean isWriteable(Class<Customer> type, Type genericType,
Annotation[] annotations, MediaType mediaType) {
return type == Customer.class;
}
}
@GET
@Produces(MediaType.APPLICATION_XML)
public Response getCustomer() {
Customer customer = customerService.getCustomer();
return Response.ok(customer).build();
}
这两个将被匹配,我们的编写器将用于转换我们的 Customer
对象
A
MessageBodyReader
implementation may be annotated withConsumes
to restrict the media types for which it will be considered suitable.Providers
implementingMessageBodyReader
contract must be either programmatically registered in a JAX-RS runtime or must be annotated with@Provider
annotation to be automatically discovered by the JAX-RS runtime during a provider scanning phase.
@Consumes
注释与作者对 @Produces
的处理相同,只是相反。相同的匹配算法。还有 @Provider
注释,同样的处理。例如
@Provider
@Consumes(MediaType.APPLICATION_XML)
public class MyJAXBMessageBodyReader
implements MessageBodyReader<Customer> {
@Override
public boolean isReadable(Class<Customer> type, Type genericType,
Annotation[] annotations, MediaType mediaType) {
return type == Customer.class
}
}
@POST
@Consumed(MediaType.APPLICATION_XML)
public Response createCustomer(Customer customer) {
customerService.save(customer);
return Response.created(newCustomerUri).build();
}
读取器将与我们的方法相匹配,并将输入流转换为 Customer
对象并将其传递给我们的方法。
就最后一个词“扫描阶段”而言,这只是 JAX_RS 实现扫描我们的包以查找要管理的组件。根据我们的配置(例如应该扫描哪些包),这种情况会在启动时发生
MessageBodyWriter
有另一个方法getSize
。如果我们不知道大小,我们可以返回-1
,框架会为我们确定大小。
如果您想以编程方式注册 MessageBodyReader
或 MessageBodyWriter
,请在 Client
或 ClientBuilder
(或任何 Configurable
实例)上使用 register
方法。
关于java - MessageBody写入器/读取器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26985183/
我想使用 通过 api 在我的应用程序中发送消息 ( https://github.com/devslopes-learn/mac-chat-api ) 当我尝试发送消息时,我总是在 Heroku 终
我已经实现了用户提供反馈的标准方式。当用户点击邮件 View Controller 中的发送或取消时,是否可以通过邮件的消息(或主题)进行搜索。如果邮件包含特定字符串,应用程序应执行操作。在这种情况下
我正在设置一个 SQS 队列,以摄取要由后端容器处理的配置数据 block 。我的第一个想法是 json.dumps 带有配置信息的字典,并通过 sqsclient.send_message() 的
我在显示 Toast 消息时遇到运行时异常 java.lang.RuntimeException: Can't create handler inside thread that has not ca
我跑 ElasticMQ在本地模拟 Amazon SQS,我想将 JSON 文件作为 MessageBody 发送。这是一个有效的示例请求: $ curl 'http://localhost:9324
我正在使用 EWS Managed API 1.2 与 Exchange 2010 和 Outlook 2010/2013 进行集成元素。我们将其与现有系统捆绑在一起。以前,我们可以选择发送 sess
iTunes Connect显示此错误: itc.olympus.partnermessage.lockey.contentprovider.contract.expiresoon.messagebo
我是一名优秀的程序员,十分优秀!