newWindowSize = spdySession.updateSendWindowSize(streamId, -1 * dataFrameSize);
// The transfer window size is pre-decremented when sending a data frame downstream.
// Close the stream on write failures that leaves the transfer window in a corrupt state.
final SocketAddress remoteAddress = e.getRemoteAddress();
final ChannelHandlerContext context = ctx;
e.getFuture().addListener(new ChannelFutureListener() {
public void operationComplete(ChannelFuture future) throws Exception {
if (!future.isSuccess()) {
issueStreamError(context, remoteAddress, streamId, SpdyStreamStatus.INTERNAL_ERROR);
}
}
});
// Close the local side of the stream if this is the last frame
if (spdyDataFrame.isLast()) {
halfCloseStream(streamId, false, e.getFuture());
}
Channels.write(ctx, e.getFuture(), spdyDataFrame, e.getRemoteAddress());
} else {
// We can send a partial frame
spdySession.updateSendWindowSize(streamId, -1 * newWindowSize);
// Create a partial data frame whose length is the current window size
SpdyDataFrame partialDataFrame = new DefaultSpdyDataFrame(streamId);
partialDataFrame.setData(spdyDataFrame.getData().readSlice(newWindowSize));
ChannelFuture writeFuture = Channels.future(e.getChannel());
// The transfer window size is pre-decremented when sending a data frame downstream.
// Close the stream on write failures that leaves the transfer window in a corrupt state.
final SocketAddress remoteAddress = e.getRemoteAddress();
final ChannelHandlerContext context = ctx;
e.getFuture().addListener(new ChannelFutureListener() {
public void operationComplete(ChannelFuture future) throws Exception {
if (!future.isSuccess()) {
issueStreamError(context, remoteAddress, streamId, SpdyStreamStatus.INTERNAL_ERROR);
}