我有類似的問題,我很驚訝沒有人在兩年內有過解決方案。我們使用的是Jersey 2.x,我用Provider
來處理Avro。
如果您生成代碼,此代碼段將起作用。如果您沒有,則必須使用 GenericDatumReader/Writer
和GenericRecord
而不是SpecificDataReader/Writer
和SpecificRecord
。
另外請注意,Avro規範聲稱使用avro/binary
作爲內容類型,儘管有一個6年的JIRA ticket來改變它,因爲它是一個無效的類型。
我把它解釋簡單,所以沒有錯誤處理。要小心,如果你有一個共同的ExceptionMapper
捕獲一般的例外,因爲它不會知道如何生成avro二進制。
@Provider
@Consumes("avro/binary")
@Produces("avro/binary")
public class AvroProvider <T extends SpecificRecord> implements MessageBodyWriter<T>, MessageBodyReader<T>
{
public boolean isWriteable(final Class<?> type, final Type genericType, final Annotation[] annotations,
final MediaType mediaType)
{
return SpecificRecord.class.isAssignableFrom(type);
}
public boolean isReadable(final Class<?> type, final Type genericType, final Annotation[] annotations,
final MediaType mediaType)
{
return true;
}
@Override
public T readFrom(Class<T> type, Type genericType, Annotation[] annotations, MediaType mediaType,
MultivaluedMap<String, String> httpHeaders, InputStream entityStream)
throws IOException, WebApplicationException
{
DatumReader<T> reader = new SpecificDatumReader<>(type);
Decoder decoder = DecoderFactory.get().binaryDecoder(entityStream, null);
return reader.read(null, decoder);
}
@SuppressWarnings("unchecked")
@Override
public void writeTo(T message, Class<?> type, Type genericType, Annotation[] annotations, MediaType mediaType,
MultivaluedMap<String, Object> httpHeaders, OutputStream entityStream)
throws IOException, WebApplicationException
{
DatumWriter<T> datumWriter = new SpecificDatumWriter<>((Class<T>)type);
Encoder encoder = EncoderFactory.get().binaryEncoder(entityStream, null);
datumWriter.write(message, encoder);
encoder.flush();
}
@Override
public long getSize(T message, Class<?> type, Type genericType, Annotation[] annotations, MediaType mediaType)
{
return -1;
}
}
來源
2016-09-13 15:55:06
max