Browse Source

Fix checkstyle violation and polish

pull/2019/head
Rossen Stoyanchev 6 years ago
parent
commit
1a37345e84
  1. 48
      spring-web/src/main/java/org/springframework/http/codec/protobuf/ProtobufDecoder.java

48
spring-web/src/main/java/org/springframework/http/codec/protobuf/ProtobufDecoder.java

@ -18,6 +18,7 @@ package org.springframework.http.codec.protobuf;
import java.io.IOException; import java.io.IOException;
import java.lang.reflect.Method; import java.lang.reflect.Method;
import java.nio.ByteBuffer;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
@ -42,25 +43,28 @@ import org.springframework.util.ConcurrentReferenceHashMap;
import org.springframework.util.MimeType; import org.springframework.util.MimeType;
/** /**
* A {@code Decoder} that reads {@link com.google.protobuf.Message}s * A {@code Decoder} that reads {@link com.google.protobuf.Message}s using
* using <a href="https://developers.google.com/protocol-buffers/">Google Protocol Buffers</a>. * <a href="https://developers.google.com/protocol-buffers/">Google Protocol Buffers</a>.
* *
* <p>Flux deserialized via * <p>Flux deserialized via
* {@link #decode(Publisher, ResolvableType, MimeType, Map)} are expected to use * {@link #decode(Publisher, ResolvableType, MimeType, Map)} are expected to use
* <a href="https://developers.google.com/protocol-buffers/docs/techniques?hl=en#streaming">delimited Protobuf messages</a> * <a href="https://developers.google.com/protocol-buffers/docs/techniques?hl=en#streaming">
* with the size of each message specified before the message itself. Single values deserialized * delimited Protobuf messages</a> with the size of each message specified before
* via {@link #decodeToMono(Publisher, ResolvableType, MimeType, Map)} are expected to use * the message itself. Single values deserialized via
* regular Protobuf message format (without the size prepended before the message). * {@link #decodeToMono(Publisher, ResolvableType, MimeType, Map)} are expected
* to use regular Protobuf message format (without the size prepended before
* the message).
* *
* <p>Notice that default instance of Protobuf message produces empty byte array, so * <p>Notice that default instance of Protobuf message produces empty byte
* {@code Mono.just(Msg.getDefaultInstance())} sent over the network will be deserialized * array, so {@code Mono.just(Msg.getDefaultInstance())} sent over the network
* as an empty {@link Mono}. * will be deserialized as an empty {@link Mono}.
* *
* <p>To generate {@code Message} Java classes, you need to install the {@code protoc} binary. * <p>To generate {@code Message} Java classes, you need to install the
* {@code protoc} binary.
* *
* <p>This decoder requires Protobuf 3 or higher, and supports * <p>This decoder requires Protobuf 3 or higher, and supports
* {@code "application/x-protobuf"} and {@code "application/octet-stream"} with the official * {@code "application/x-protobuf"} and {@code "application/octet-stream"} with
* {@code "com.google.protobuf:protobuf-java"} library. * the official {@code "com.google.protobuf:protobuf-java"} library.
* *
* @author Sébastien Deleuze * @author Sébastien Deleuze
* @since 5.1 * @since 5.1
@ -68,9 +72,7 @@ import org.springframework.util.MimeType;
*/ */
public class ProtobufDecoder extends ProtobufCodecSupport implements Decoder<Message> { public class ProtobufDecoder extends ProtobufCodecSupport implements Decoder<Message> {
/** /** The default max size for aggregating messages. */
* The default max size for aggregating messages.
*/
protected static final int DEFAULT_MESSAGE_MAX_SIZE = 64 * 1024; protected static final int DEFAULT_MESSAGE_MAX_SIZE = 64 * 1024;
private static final ConcurrentMap<Class<?>, Method> methodCache = new ConcurrentReferenceHashMap<>(); private static final ConcurrentMap<Class<?>, Method> methodCache = new ConcurrentReferenceHashMap<>();
@ -123,7 +125,8 @@ public class ProtobufDecoder extends ProtobufCodecSupport implements Decoder<Mes
return DataBufferUtils.join(inputStream).map(dataBuffer -> { return DataBufferUtils.join(inputStream).map(dataBuffer -> {
try { try {
Message.Builder builder = getMessageBuilder(elementType.toClass()); Message.Builder builder = getMessageBuilder(elementType.toClass());
builder.mergeFrom(CodedInputStream.newInstance(dataBuffer.asByteBuffer()), this.extensionRegistry); ByteBuffer buffer = dataBuffer.asByteBuffer();
builder.mergeFrom(CodedInputStream.newInstance(buffer), this.extensionRegistry);
return builder.build(); return builder.build();
} }
catch (IOException ex) { catch (IOException ex) {
@ -131,7 +134,8 @@ public class ProtobufDecoder extends ProtobufCodecSupport implements Decoder<Mes
} }
catch (Exception ex) { catch (Exception ex) {
throw new DecodingException("Could not read Protobuf message: " + ex.getMessage(), ex); throw new DecodingException("Could not read Protobuf message: " + ex.getMessage(), ex);
} finally { }
finally {
DataBufferUtils.release(dataBuffer); DataBufferUtils.release(dataBuffer);
} }
} }
@ -168,11 +172,13 @@ public class ProtobufDecoder extends ProtobufCodecSupport implements Decoder<Mes
private int messageBytesToRead; private int messageBytesToRead;
public MessageDecoderFunction(ResolvableType elementType, int maxMessageSize) { public MessageDecoderFunction(ResolvableType elementType, int maxMessageSize) {
this.elementType = elementType; this.elementType = elementType;
this.maxMessageSize = maxMessageSize; this.maxMessageSize = maxMessageSize;
} }
@Override @Override
public Iterable<? extends Message> apply(DataBuffer input) { public Iterable<? extends Message> apply(DataBuffer input) {
try { try {
@ -189,8 +195,9 @@ public class ProtobufDecoder extends ProtobufCodecSupport implements Decoder<Mes
this.messageBytesToRead = CodedInputStream.readRawVarint32(firstByte, input.asInputStream()); this.messageBytesToRead = CodedInputStream.readRawVarint32(firstByte, input.asInputStream());
if (this.messageBytesToRead > this.maxMessageSize) { if (this.messageBytesToRead > this.maxMessageSize) {
throw new DecodingException( throw new DecodingException(
"The number of bytes to read parsed in the incoming stream (" + "The number of bytes to read from the incoming stream " +
this.messageBytesToRead + ") exceeds the configured limit (" + this.maxMessageSize + ")"); "(" + this.messageBytesToRead + ") exceeds " +
"the configured limit (" + this.maxMessageSize + ")");
} }
this.output = input.factory().allocateBuffer(this.messageBytesToRead); this.output = input.factory().allocateBuffer(this.messageBytesToRead);
} }
@ -206,7 +213,8 @@ public class ProtobufDecoder extends ProtobufCodecSupport implements Decoder<Mes
if (this.messageBytesToRead == 0) { if (this.messageBytesToRead == 0) {
Message.Builder builder = getMessageBuilder(this.elementType.toClass()); Message.Builder builder = getMessageBuilder(this.elementType.toClass());
builder.mergeFrom(CodedInputStream.newInstance(this.output.asByteBuffer()), extensionRegistry); ByteBuffer buffer = this.output.asByteBuffer();
builder.mergeFrom(CodedInputStream.newInstance(buffer), extensionRegistry);
messages.add(builder.build()); messages.add(builder.build());
DataBufferUtils.release(this.output); DataBufferUtils.release(this.output);
this.output = null; this.output = null;

Loading…
Cancel
Save