Javadocs.
This commit is contained in:
parent
111ae7fa1a
commit
726fda5593
|
@ -34,7 +34,14 @@ public class Promise<T> implements Handler<T>, Future<T>
|
|||
@Override
|
||||
public void completed(T result)
|
||||
{
|
||||
fulfilled(result);
|
||||
this.promise = result;
|
||||
latch.countDown();
|
||||
}
|
||||
|
||||
public void failed(Throwable x, T context)
|
||||
{
|
||||
this.failure = x;
|
||||
latch.countDown();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -78,16 +85,4 @@ public class Promise<T> implements Handler<T>, Future<T>
|
|||
throw new ExecutionException(failure);
|
||||
return promise;
|
||||
}
|
||||
|
||||
public void failed(Throwable x)
|
||||
{
|
||||
this.failure = x;
|
||||
latch.countDown();
|
||||
}
|
||||
|
||||
public void fulfilled(T promise)
|
||||
{
|
||||
this.promise = promise;
|
||||
latch.countDown();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -140,7 +140,7 @@ public class StandardSession implements ISession, Parser.Listener, Handler<Stand
|
|||
catch (StreamException x)
|
||||
{
|
||||
removeStream(stream);
|
||||
handler.failed(x);
|
||||
handler.failed(x, stream);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -174,7 +174,7 @@ public class StandardSession implements ISession, Parser.Listener, Handler<Stand
|
|||
catch (StreamException x)
|
||||
{
|
||||
logger.info("Could not send reset on stream " + rstInfo.getStreamId(), x);
|
||||
handler.failed(x);
|
||||
handler.failed(x, null);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -197,7 +197,7 @@ public class StandardSession implements ISession, Parser.Listener, Handler<Stand
|
|||
}
|
||||
catch (StreamException x)
|
||||
{
|
||||
handler.failed(x);
|
||||
handler.failed(x, null);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -212,17 +212,17 @@ public class StandardSession implements ISession, Parser.Listener, Handler<Stand
|
|||
@Override
|
||||
public void ping(final Handler<PingInfo> handler)
|
||||
{
|
||||
int pingId = pingIds.getAndAdd(2);
|
||||
PingInfo pingInfo = new PingInfo(pingId);
|
||||
try
|
||||
{
|
||||
int pingId = pingIds.getAndAdd(2);
|
||||
final PingInfo pingInfo = new PingInfo(pingId);
|
||||
PingFrame frame = new PingFrame(version, pingId);
|
||||
control(null, frame, handler, pingInfo);
|
||||
flush();
|
||||
}
|
||||
catch (StreamException x)
|
||||
{
|
||||
handler.failed(x);
|
||||
handler.failed(x, pingInfo);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -250,7 +250,7 @@ public class StandardSession implements ISession, Parser.Listener, Handler<Stand
|
|||
}
|
||||
catch (StreamException x)
|
||||
{
|
||||
handler.failed(x);
|
||||
handler.failed(x, null);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -730,7 +730,7 @@ public class StandardSession implements ISession, Parser.Listener, Handler<Stand
|
|||
}
|
||||
|
||||
@Override
|
||||
public void failed(Throwable x)
|
||||
public void failed(Throwable x, FrameBytes frameBytes)
|
||||
{
|
||||
throw new SPDYException(x);
|
||||
}
|
||||
|
|
|
@ -286,7 +286,7 @@ public class StandardStream implements IStream
|
|||
catch (StreamException x)
|
||||
{
|
||||
logger.debug("Could not send reply on stream " + this, x);
|
||||
handler.failed(x);
|
||||
handler.failed(x, null);
|
||||
session.rst(new RstInfo(getId(), x.getStreamStatus()));
|
||||
}
|
||||
}
|
||||
|
@ -327,7 +327,7 @@ public class StandardStream implements IStream
|
|||
catch (StreamException x)
|
||||
{
|
||||
logger.debug("Could not send headers on stream " + this, x);
|
||||
handler.failed(x);
|
||||
handler.failed(x, null);
|
||||
session.rst(new RstInfo(getId(), x.getStreamStatus()));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -18,6 +18,9 @@ package org.eclipse.jetty.spdy.api;
|
|||
|
||||
import java.nio.ByteBuffer;
|
||||
|
||||
/**
|
||||
* <p>Specialized {@link DataInfo} for {@link ByteBuffer} content.</p>
|
||||
*/
|
||||
public class ByteBufferDataInfo extends DataInfo
|
||||
{
|
||||
private ByteBuffer buffer;
|
||||
|
@ -34,13 +37,13 @@ public class ByteBufferDataInfo extends DataInfo
|
|||
}
|
||||
|
||||
@Override
|
||||
public int getBytesCount()
|
||||
public int getContentLength()
|
||||
{
|
||||
return buffer.remaining();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getBytes(ByteBuffer output)
|
||||
public int getContent(ByteBuffer output)
|
||||
{
|
||||
int length = output.remaining();
|
||||
if (buffer.remaining() > length)
|
||||
|
|
|
@ -18,6 +18,9 @@ package org.eclipse.jetty.spdy.api;
|
|||
|
||||
import java.nio.ByteBuffer;
|
||||
|
||||
/**
|
||||
* <p>Specialized {@link DataInfo} for byte array content.</p>
|
||||
*/
|
||||
public class BytesDataInfo extends DataInfo
|
||||
{
|
||||
private byte[] bytes;
|
||||
|
@ -35,13 +38,13 @@ public class BytesDataInfo extends DataInfo
|
|||
}
|
||||
|
||||
@Override
|
||||
public int getBytesCount()
|
||||
public int getContentLength()
|
||||
{
|
||||
return bytes.length - offset;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getBytes(ByteBuffer output)
|
||||
public int getContent(ByteBuffer output)
|
||||
{
|
||||
int remaining = output.remaining();
|
||||
int length = Math.min(bytes.length - offset, remaining);
|
||||
|
|
|
@ -19,88 +19,171 @@ package org.eclipse.jetty.spdy.api;
|
|||
import java.nio.ByteBuffer;
|
||||
import java.nio.charset.Charset;
|
||||
|
||||
/**
|
||||
* <p>A container for DATA frames metadata and content bytes.</p>
|
||||
* <p>Specialized subclasses (like {@link StringDataInfo}) may be used by applications
|
||||
* to send specific types of content.</p>
|
||||
* <p>Applications may send multiple instances of {@link DataInfo}, usually of the same
|
||||
* type, via {@link Stream#data(DataInfo)}. The last instance must have the
|
||||
* {@link #isClose() close flag} set, so that the client knows that no more content is
|
||||
* expected.</p>
|
||||
*/
|
||||
public abstract class DataInfo
|
||||
{
|
||||
public final static byte FLAG_FIN = 1;
|
||||
/**
|
||||
* <p>Flag that indicates that this {@link DataInfo} is the last frame in the stream.</p>
|
||||
*
|
||||
* @see #isClose()
|
||||
* @see #getFlags()
|
||||
*/
|
||||
public final static byte FLAG_CLOSE = 1;
|
||||
/**
|
||||
* <p>Flag that indicates that this {@link DataInfo}'s data is compressed.</p>
|
||||
*
|
||||
* @see #isCompress()
|
||||
* @see #getFlags()
|
||||
*/
|
||||
public final static byte FLAG_COMPRESS = 2;
|
||||
|
||||
private boolean close;
|
||||
private boolean compress;
|
||||
private boolean consumed;
|
||||
|
||||
/**
|
||||
* <p>Creates a new {@link DataInfo} with the given close flag and no compression flag.</p>
|
||||
*
|
||||
* @param close the value of the close flag
|
||||
*/
|
||||
public DataInfo(boolean close)
|
||||
{
|
||||
setClose(close);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Creates a new {@link DataInfo} with the given close flag and given compression flag.</p>
|
||||
*
|
||||
* @param close the close flag
|
||||
* @param compress the compress flag
|
||||
*/
|
||||
public DataInfo(boolean close, boolean compress)
|
||||
{
|
||||
setClose(close);
|
||||
setCompress(compress);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the value of the compress flag
|
||||
* @see #setCompress(boolean)
|
||||
*/
|
||||
public boolean isCompress()
|
||||
{
|
||||
return compress;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param compress the value of the compress flag
|
||||
* @see #isCompress()
|
||||
*/
|
||||
public void setCompress(boolean compress)
|
||||
{
|
||||
this.compress = compress;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the value of the close flag
|
||||
* @see #setClose(boolean)
|
||||
*/
|
||||
public boolean isClose()
|
||||
{
|
||||
return close;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param close the value of the close flag
|
||||
* @see #isClose()
|
||||
*/
|
||||
public void setClose(boolean close)
|
||||
{
|
||||
this.close = close;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the close and compress flags as integer
|
||||
* @see #FLAG_CLOSE
|
||||
* @see #FLAG_COMPRESS
|
||||
*/
|
||||
public byte getFlags()
|
||||
{
|
||||
byte flags = isClose() ? FLAG_FIN : 0;
|
||||
byte flags = isClose() ? FLAG_CLOSE : 0;
|
||||
flags |= isCompress() ? FLAG_COMPRESS : 0;
|
||||
return flags;
|
||||
}
|
||||
|
||||
public abstract int getBytesCount();
|
||||
/**
|
||||
* @return the length of the content bytes
|
||||
* @see #getContent(ByteBuffer)
|
||||
*/
|
||||
public abstract int getContentLength();
|
||||
|
||||
public abstract int getBytes(ByteBuffer output);
|
||||
/**
|
||||
* <p>Copies the content bytes of this {@link DataInfo} into the given {@link ByteBuffer}.</p>
|
||||
* <p>If the given {@link ByteBuffer} cannot contain the whole content of this {@link DataInfo}
|
||||
* then this {@link DataInfo} will not be {@link #isConsumed() consumed}, and further content
|
||||
* may be retrieved by invoking again this method.</p>
|
||||
*
|
||||
* @param output the {@link ByteBuffer} to copy to bytes into
|
||||
* @return the number of bytes copied
|
||||
* @see #getContentLength()
|
||||
*/
|
||||
public abstract int getContent(ByteBuffer output);
|
||||
|
||||
/**
|
||||
* @param charset the charset used to convert the bytes
|
||||
* @return a String with the content of this {@link DataInfo}
|
||||
*/
|
||||
public String asString(String charset)
|
||||
{
|
||||
ByteBuffer buffer = ByteBuffer.allocate(getBytesCount());
|
||||
getBytes(buffer);
|
||||
ByteBuffer buffer = ByteBuffer.allocate(getContentLength());
|
||||
getContent(buffer);
|
||||
buffer.flip();
|
||||
return Charset.forName(charset).decode(buffer).toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* @return a byte array with the content of this {@link DataInfo}
|
||||
*/
|
||||
public byte[] asBytes()
|
||||
{
|
||||
ByteBuffer buffer = ByteBuffer.allocate(getBytesCount());
|
||||
getBytes(buffer);
|
||||
ByteBuffer buffer = ByteBuffer.allocate(getContentLength());
|
||||
getContent(buffer);
|
||||
buffer.flip();
|
||||
byte[] result = new byte[buffer.remaining()];
|
||||
buffer.get(result);
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return a {@link ByteBuffer} with the content of this {@link DataInfo}
|
||||
*/
|
||||
public ByteBuffer asByteBuffer()
|
||||
{
|
||||
ByteBuffer buffer = ByteBuffer.allocate(getBytesCount());
|
||||
getBytes(buffer);
|
||||
ByteBuffer buffer = ByteBuffer.allocate(getContentLength());
|
||||
getContent(buffer);
|
||||
buffer.flip();
|
||||
return buffer;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return whether this {@link DataInfo}'s content has been consumed
|
||||
*/
|
||||
public boolean isConsumed()
|
||||
{
|
||||
return consumed;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param consumed whether this {@link DataInfo}'s content has been consumed
|
||||
*/
|
||||
protected void setConsumed(boolean consumed)
|
||||
{
|
||||
this.consumed = consumed;
|
||||
|
@ -109,6 +192,6 @@ public abstract class DataInfo
|
|||
@Override
|
||||
public String toString()
|
||||
{
|
||||
return String.format("DATA @%x length=%d close=%b compress=%b", hashCode(), getBytesCount(), isClose(), isCompress());
|
||||
return String.format("DATA @%x length=%d close=%b compress=%b", hashCode(), getContentLength(), isClose(), isCompress());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,22 +16,38 @@
|
|||
|
||||
package org.eclipse.jetty.spdy.api;
|
||||
|
||||
/**
|
||||
* <p>A container for GOAWAY frames metadata: the last good stream id and
|
||||
* the session status.</p>
|
||||
*/
|
||||
public class GoAwayInfo
|
||||
{
|
||||
private final int lastStreamId;
|
||||
private final SessionStatus sessionStatus;
|
||||
|
||||
/**
|
||||
* <p>Creates a new {@link GoAwayInfo} with the given last good stream id and session status</p>
|
||||
*
|
||||
* @param lastStreamId the last good stream id
|
||||
* @param sessionStatus the session status
|
||||
*/
|
||||
public GoAwayInfo(int lastStreamId, SessionStatus sessionStatus)
|
||||
{
|
||||
this.lastStreamId = lastStreamId;
|
||||
this.sessionStatus = sessionStatus;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the last good stream id
|
||||
*/
|
||||
public int getLastStreamId()
|
||||
{
|
||||
return lastStreamId;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the session status
|
||||
*/
|
||||
public SessionStatus getSessionStatus()
|
||||
{
|
||||
return sessionStatus;
|
||||
|
|
|
@ -16,12 +16,36 @@
|
|||
|
||||
package org.eclipse.jetty.spdy.api;
|
||||
|
||||
/**
|
||||
* <p>A callback abstraction that handles completed/failed events of asynchronous operations.</p>
|
||||
* <p>Instances of this class capture a context that is made available on completion
|
||||
* and failure callbacks.</p>
|
||||
*
|
||||
* @param <C> the type of the context object
|
||||
*/
|
||||
public interface Handler<C>
|
||||
{
|
||||
/**
|
||||
* <p>Callback invoked when the operation completes.</p>
|
||||
*
|
||||
* @param context the context
|
||||
* @see #failed(Throwable, Object)
|
||||
*/
|
||||
public abstract void completed(C context);
|
||||
|
||||
public void failed(Throwable x);
|
||||
/**
|
||||
* <p>Callback invoked when the operation fails.</p>
|
||||
*
|
||||
* @param x the reason for the operation failure
|
||||
* @param context the context
|
||||
*/
|
||||
public void failed(Throwable x, C context);
|
||||
|
||||
/**
|
||||
* <p>Empty implementation of {@link Handler}</p>
|
||||
*
|
||||
* @param <C> the type of the context object
|
||||
*/
|
||||
public static class Adapter<C> implements Handler<C>
|
||||
{
|
||||
@Override
|
||||
|
@ -30,7 +54,7 @@ public interface Handler<C>
|
|||
}
|
||||
|
||||
@Override
|
||||
public void failed(Throwable x)
|
||||
public void failed(Throwable x, C context)
|
||||
{
|
||||
throw new SPDYException(x);
|
||||
}
|
||||
|
|
|
@ -24,15 +24,32 @@ import java.util.LinkedHashSet;
|
|||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* <p>A container for name/value pairs, known as headers.</p>
|
||||
* <p>A {@link Header} is composed of a case-insensitive name string and
|
||||
* of a case-sensitive set of value strings.</p>
|
||||
* <p>The implementation of this class is not thread safe.</p>
|
||||
*/
|
||||
public class Headers implements Iterable<Headers.Header>
|
||||
{
|
||||
private final Map<String, Header> headers;
|
||||
|
||||
/**
|
||||
* <p>Creates an empty modifiable {@link Headers} instance.</p>
|
||||
* @see #Headers(Headers, boolean)
|
||||
*/
|
||||
public Headers()
|
||||
{
|
||||
headers = new LinkedHashMap<>();
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Creates a {@link Headers} instance by copying the headers from the given
|
||||
* {@link Headers} and making it (im)mutable depending on the given {@code immutable} parameter</p>
|
||||
*
|
||||
* @param original the {@link Headers} to copy headers from
|
||||
* @param immutable whether this instance is immutable
|
||||
*/
|
||||
public Headers(Headers original, boolean immutable)
|
||||
{
|
||||
Map<String, Header> copy = new LinkedHashMap<>();
|
||||
|
@ -57,19 +74,32 @@ public class Headers implements Iterable<Headers.Header>
|
|||
return headers.hashCode();
|
||||
}
|
||||
|
||||
/**
|
||||
* @return a set of header names
|
||||
*/
|
||||
public Set<String> names()
|
||||
{
|
||||
Set<String> result = new LinkedHashSet<String>();
|
||||
Set<String> result = new LinkedHashSet<>();
|
||||
for (Header header : headers.values())
|
||||
result.add(header.name);
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param name the header name
|
||||
* @return the {@link Header} with the given name, or null if no such header exists
|
||||
*/
|
||||
public Header get(String name)
|
||||
{
|
||||
return headers.get(name.trim().toLowerCase());
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Inserts or replaces the given name/value pair as a single-valued {@link Header}.</p>
|
||||
*
|
||||
* @param name the header name
|
||||
* @param value the header value
|
||||
*/
|
||||
public void put(String name, String value)
|
||||
{
|
||||
name = name.trim();
|
||||
|
@ -77,12 +107,23 @@ public class Headers implements Iterable<Headers.Header>
|
|||
headers.put(name.toLowerCase(), header);
|
||||
}
|
||||
|
||||
public void put(String name, Header header)
|
||||
/**
|
||||
* <p>Inserts or replaces the given {@link Header}, mapped to the {@link Header#name() header's name}</p>
|
||||
*
|
||||
* @param header the header to add
|
||||
*/
|
||||
public void put(Header header)
|
||||
{
|
||||
name = name.trim();
|
||||
headers.put(name.toLowerCase(), header);
|
||||
headers.put(header.name().toLowerCase(), header);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Adds the given value to a header with the given name, creating a {@link Header} is none exists
|
||||
* for the given name.</p>
|
||||
*
|
||||
* @param name the header name
|
||||
* @param value the header value to add
|
||||
*/
|
||||
public void add(String name, String value)
|
||||
{
|
||||
name = name.trim();
|
||||
|
@ -99,27 +140,46 @@ public class Headers implements Iterable<Headers.Header>
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Removes the {@link Header} with the given name</p>
|
||||
*
|
||||
* @param name the name of the header to remove
|
||||
* @return the removed header, or null if no such header existed
|
||||
*/
|
||||
public Header remove(String name)
|
||||
{
|
||||
name = name.trim();
|
||||
return headers.remove(name.toLowerCase());
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Empties this {@link Headers} instance from all headers</p>
|
||||
* @see #isEmpty()
|
||||
*/
|
||||
public void clear()
|
||||
{
|
||||
headers.clear();
|
||||
}
|
||||
|
||||
/**
|
||||
* @return whether this {@link Headers} instance is empty
|
||||
*/
|
||||
public boolean isEmpty()
|
||||
{
|
||||
return headers.isEmpty();
|
||||
}
|
||||
|
||||
public int getSize()
|
||||
/**
|
||||
* @return the number of headers
|
||||
*/
|
||||
public int size()
|
||||
{
|
||||
return headers.size();
|
||||
}
|
||||
|
||||
/**
|
||||
* @return an iterator over the {@link Header} present in this instance
|
||||
*/
|
||||
@Override
|
||||
public Iterator<Header> iterator()
|
||||
{
|
||||
|
@ -132,6 +192,10 @@ public class Headers implements Iterable<Headers.Header>
|
|||
return headers.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>A named list of string values.</p>
|
||||
* <p>The name is case-sensitive and there must be at least one value.</p>
|
||||
*/
|
||||
public static class Header
|
||||
{
|
||||
private final String name;
|
||||
|
@ -165,11 +229,17 @@ public class Headers implements Iterable<Headers.Header>
|
|||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the header's name
|
||||
*/
|
||||
public String name()
|
||||
{
|
||||
return name;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the first header's value
|
||||
*/
|
||||
public String value()
|
||||
{
|
||||
return values[0];
|
||||
|
@ -189,11 +259,17 @@ public class Headers implements Iterable<Headers.Header>
|
|||
return value == null ? null : Integer.valueOf(value);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the header's values
|
||||
*/
|
||||
public String[] values()
|
||||
{
|
||||
return values;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return whether the header has multiple values
|
||||
*/
|
||||
public boolean hasMultipleValues()
|
||||
{
|
||||
return values.length > 1;
|
||||
|
|
|
@ -16,20 +16,50 @@
|
|||
|
||||
package org.eclipse.jetty.spdy.api;
|
||||
|
||||
/**
|
||||
* <p>A container for HEADERS frame metadata and headers.</p>
|
||||
*/
|
||||
public class HeadersInfo
|
||||
{
|
||||
public static final byte FLAG_FIN = 1;
|
||||
/**
|
||||
* <p>Flag that indicates that this {@link HeadersInfo} is the last frame in the stream.</p>
|
||||
*
|
||||
* @see #isClose()
|
||||
* @see #getFlags()
|
||||
*/
|
||||
public static final byte FLAG_CLOSE = 1;
|
||||
/**
|
||||
* <p>Flag that indicates that the compression of the stream must be reset.</p>
|
||||
*
|
||||
* @see #isResetCompression()
|
||||
* @see #getFlags()
|
||||
*/
|
||||
public static final byte FLAG_RESET_COMPRESSION = 2;
|
||||
|
||||
private final boolean close;
|
||||
private final boolean resetCompression;
|
||||
private final Headers headers;
|
||||
|
||||
/**
|
||||
* <p>Creates a new {@link HeadersInfo} instance with the given headers,
|
||||
* the given close flag and no reset compression flag</p>
|
||||
*
|
||||
* @param headers the {@link Headers}
|
||||
* @param close the value of the close flag
|
||||
*/
|
||||
public HeadersInfo(Headers headers, boolean close)
|
||||
{
|
||||
this(headers, close, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Creates a new {@link HeadersInfo} instance with the given headers,
|
||||
* the given close flag and the given reset compression flag</p>
|
||||
*
|
||||
* @param headers the {@link Headers}
|
||||
* @param close the value of the close flag
|
||||
* @param resetCompression the value of the reset compression flag
|
||||
*/
|
||||
public HeadersInfo(Headers headers, boolean close, boolean resetCompression)
|
||||
{
|
||||
this.headers = headers;
|
||||
|
@ -37,24 +67,38 @@ public class HeadersInfo
|
|||
this.resetCompression = resetCompression;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the value of the close flag
|
||||
*/
|
||||
public boolean isClose()
|
||||
{
|
||||
return close;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the value of the reset compression flag
|
||||
*/
|
||||
public boolean isResetCompression()
|
||||
{
|
||||
return resetCompression;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the {@link Headers}
|
||||
*/
|
||||
public Headers getHeaders()
|
||||
{
|
||||
return headers;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the close and reset compression flags as integer
|
||||
* @see #FLAG_CLOSE
|
||||
* @see #FLAG_RESET_COMPRESSION
|
||||
*/
|
||||
public byte getFlags()
|
||||
{
|
||||
byte flags = isClose() ? FLAG_FIN : 0;
|
||||
byte flags = isClose() ? FLAG_CLOSE : 0;
|
||||
flags += isResetCompression() ? FLAG_RESET_COMPRESSION : 0;
|
||||
return flags;
|
||||
}
|
||||
|
|
|
@ -16,15 +16,25 @@
|
|||
|
||||
package org.eclipse.jetty.spdy.api;
|
||||
|
||||
/**
|
||||
* <p>A container for PING frames data.</p>
|
||||
*/
|
||||
public class PingInfo
|
||||
{
|
||||
private final int pingId;
|
||||
|
||||
/**
|
||||
* <p>Creates a {@link PingInfo} with the given ping id</p>
|
||||
* @param pingId the ping id
|
||||
*/
|
||||
public PingInfo(int pingId)
|
||||
{
|
||||
this.pingId = pingId;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the ping id
|
||||
*/
|
||||
public int getPingId()
|
||||
{
|
||||
return pingId;
|
||||
|
|
|
@ -16,37 +16,67 @@
|
|||
|
||||
package org.eclipse.jetty.spdy.api;
|
||||
|
||||
/**
|
||||
* <p>A container for SYN_REPLY frames metadata and headers.</p>
|
||||
*/
|
||||
public class ReplyInfo
|
||||
{
|
||||
public static final byte FLAG_FIN = 1;
|
||||
/**
|
||||
* <p>Flag that indicates that this {@link ReplyInfo} is the last frame in the stream.</p>
|
||||
*
|
||||
* @see #isClose()
|
||||
* @see #getFlags()
|
||||
*/
|
||||
public static final byte FLAG_CLOSE = 1;
|
||||
|
||||
private final Headers headers;
|
||||
private final boolean close;
|
||||
|
||||
/**
|
||||
* <p>Creates a new {@link ReplyInfo} instance with empty headers and the given close flag.</p>
|
||||
*
|
||||
* @param close the value of the close flag
|
||||
*/
|
||||
public ReplyInfo(boolean close)
|
||||
{
|
||||
this(new Headers(), close);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Creates a {@link ReplyInfo} instance with the given headers and the given close flag.</p>
|
||||
*
|
||||
* @param headers the {@link Headers}
|
||||
* @param close the value of the close flag
|
||||
*/
|
||||
public ReplyInfo(Headers headers, boolean close)
|
||||
{
|
||||
this.headers = headers;
|
||||
this.close = close;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the {@link Headers}
|
||||
*/
|
||||
public Headers getHeaders()
|
||||
{
|
||||
return headers;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the value of the close flag
|
||||
*/
|
||||
public boolean isClose()
|
||||
{
|
||||
return close;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the close and reset compression flags as integer
|
||||
* @see #FLAG_CLOSE
|
||||
*/
|
||||
public byte getFlags()
|
||||
{
|
||||
return isClose() ? FLAG_FIN : 0;
|
||||
return isClose() ? FLAG_CLOSE : 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -16,22 +16,37 @@
|
|||
|
||||
package org.eclipse.jetty.spdy.api;
|
||||
|
||||
/**
|
||||
* <p>A container for RST_STREAM frames data: the stream id and the stream status.</p>
|
||||
*/
|
||||
public class RstInfo
|
||||
{
|
||||
private final int streamId;
|
||||
private final StreamStatus streamStatus;
|
||||
|
||||
/**
|
||||
* <p>Creates a new {@link RstInfo} with the given stream id and stream status</p>
|
||||
*
|
||||
* @param streamId the stream id
|
||||
* @param streamStatus the stream status
|
||||
*/
|
||||
public RstInfo(int streamId, StreamStatus streamStatus)
|
||||
{
|
||||
this.streamId = streamId;
|
||||
this.streamStatus = streamStatus;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the stream id
|
||||
*/
|
||||
public int getStreamId()
|
||||
{
|
||||
return streamId;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the stream status
|
||||
*/
|
||||
public StreamStatus getStreamStatus()
|
||||
{
|
||||
return streamStatus;
|
||||
|
|
|
@ -18,7 +18,7 @@ package org.eclipse.jetty.spdy.api;
|
|||
|
||||
/**
|
||||
* <p>An unrecoverable exception that signals to the application that
|
||||
* something wrong happened</p>
|
||||
* something wrong happened.</p>
|
||||
*/
|
||||
public class SPDYException extends RuntimeException
|
||||
{
|
||||
|
|
|
@ -19,11 +19,25 @@ package org.eclipse.jetty.spdy.api;
|
|||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* <p>An enumeration of session statuses.</p>
|
||||
*/
|
||||
public enum SessionStatus
|
||||
{
|
||||
/**
|
||||
* <p>The session status indicating no errors</p>
|
||||
*/
|
||||
OK(0),
|
||||
/**
|
||||
* <p>The session status indicating a protocol error</p>
|
||||
*/
|
||||
PROTOCOL_ERROR(1);
|
||||
|
||||
/**
|
||||
* @param code the session status code
|
||||
* @return a {@link SessionStatus} from the given code,
|
||||
* or null if no status exists
|
||||
*/
|
||||
public static SessionStatus from(int code)
|
||||
{
|
||||
return Mapper.codes.get(code);
|
||||
|
@ -37,6 +51,9 @@ public enum SessionStatus
|
|||
Mapper.codes.put(code, this);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the code of this {@link SessionStatus}
|
||||
*/
|
||||
public int getCode()
|
||||
{
|
||||
return code;
|
||||
|
|
|
@ -19,18 +19,62 @@ package org.eclipse.jetty.spdy.api;
|
|||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* <p>An enumeration of stream statuses.</p>
|
||||
*/
|
||||
public enum StreamStatus
|
||||
{
|
||||
/**
|
||||
* <p>The stream status indicating a protocol error</p>
|
||||
*/
|
||||
PROTOCOL_ERROR(1, 1),
|
||||
/**
|
||||
* <p>The stream status indicating that the stream is not valid</p>
|
||||
*/
|
||||
INVALID_STREAM(2, 2),
|
||||
/**
|
||||
* <p>The stream status indicating that the stream has been refused</p>
|
||||
*/
|
||||
REFUSED_STREAM(3, 3),
|
||||
/**
|
||||
* <p>The stream status indicating that the implementation does not support the SPDY version of the stream</p>
|
||||
*/
|
||||
UNSUPPORTED_VERSION(4, 4),
|
||||
/**
|
||||
* <p>The stream status indicating that the stream is no longer needed</p>
|
||||
*/
|
||||
CANCEL_STREAM(5, 5),
|
||||
INTERNAL_ERROR(6, -1),
|
||||
/**
|
||||
* <p>The stream status indicating an implementation error</p>
|
||||
*/
|
||||
INTERNAL_ERROR(6, 11),
|
||||
/**
|
||||
* <p>The stream status indicating a flow control error</p>
|
||||
*/
|
||||
FLOW_CONTROL_ERROR(7, 6),
|
||||
/**
|
||||
* <p>The stream status indicating a stream opened more than once</p>
|
||||
*/
|
||||
STREAM_IN_USE(-1, 7),
|
||||
STREAM_ALREADY_CLOSED(-1, 8);
|
||||
/**
|
||||
* <p>The stream status indicating data on a stream already closed</p>
|
||||
*/
|
||||
STREAM_ALREADY_CLOSED(-1, 8),
|
||||
/**
|
||||
* <p>The stream status indicating credentials not valid</p>
|
||||
*/
|
||||
INVALID_CREDENTIALS(-1, 9),
|
||||
/**
|
||||
* <p>The stream status indicating that the implementation could not support a frame too large</p>
|
||||
*/
|
||||
FRAME_TOO_LARGE(-1, 10);
|
||||
|
||||
/**
|
||||
* @param version the SPDY protocol version
|
||||
* @param code the stream status code
|
||||
* @return a {@link StreamStatus} from the given version and code,
|
||||
* or null if no such status exists
|
||||
*/
|
||||
public static StreamStatus from(short version, int code)
|
||||
{
|
||||
switch (version)
|
||||
|
@ -57,6 +101,10 @@ public enum StreamStatus
|
|||
Mapper.v3Codes.put(v3Code, this);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param version the SPDY protocol version
|
||||
* @return the stream status code
|
||||
*/
|
||||
public int getCode(short version)
|
||||
{
|
||||
switch (version)
|
||||
|
|
|
@ -19,6 +19,9 @@ package org.eclipse.jetty.spdy.api;
|
|||
import java.nio.ByteBuffer;
|
||||
import java.nio.charset.Charset;
|
||||
|
||||
/**
|
||||
* <p>Specialized {@link DataInfo} for {@link String} content.</p>
|
||||
*/
|
||||
public class StringDataInfo extends DataInfo
|
||||
{
|
||||
private byte[] bytes;
|
||||
|
@ -36,13 +39,13 @@ public class StringDataInfo extends DataInfo
|
|||
}
|
||||
|
||||
@Override
|
||||
public int getBytesCount()
|
||||
public int getContentLength()
|
||||
{
|
||||
return bytes.length - offset;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getBytes(ByteBuffer output)
|
||||
public int getContent(ByteBuffer output)
|
||||
{
|
||||
int remaining = output.remaining();
|
||||
int length = Math.min(bytes.length - offset, remaining);
|
||||
|
|
|
@ -16,9 +16,18 @@
|
|||
|
||||
package org.eclipse.jetty.spdy.api;
|
||||
|
||||
/**
|
||||
* <p>A container for SYN_STREAM frames metadata and data.</p>
|
||||
*/
|
||||
public class SynInfo
|
||||
{
|
||||
public static final byte FLAG_FIN = 1;
|
||||
/**
|
||||
* <p>Flag that indicates that this {@link DataInfo} is the last frame in the stream.</p>
|
||||
*
|
||||
* @see #isClose()
|
||||
* @see #getFlags()
|
||||
*/
|
||||
public static final byte FLAG_CLOSE = 1;
|
||||
public static final byte FLAG_UNIDIRECTIONAL = 2;
|
||||
|
||||
private final boolean close;
|
||||
|
@ -27,16 +36,39 @@ public class SynInfo
|
|||
private final byte priority;
|
||||
private final Headers headers;
|
||||
|
||||
/**
|
||||
* <p>Creates a new {@link SynInfo} instance with empty headers and the given close flag,
|
||||
* not unidirectional, without associated stream, and with default priority.</p>
|
||||
*
|
||||
* @param close the value of the close flag
|
||||
*/
|
||||
public SynInfo(boolean close)
|
||||
{
|
||||
this(new Headers(), close);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Creates a {@link ReplyInfo} instance with the given headers and the given close flag,
|
||||
* not unidirectional, without associated stream, and with default priority.</p>
|
||||
*
|
||||
* @param headers the {@link Headers}
|
||||
* @param close the value of the close flag
|
||||
*/
|
||||
public SynInfo(Headers headers, boolean close)
|
||||
{
|
||||
this(headers, close, false, 0, (byte)0);
|
||||
}
|
||||
|
||||
/**
|
||||
* <p>Creates a {@link ReplyInfo} instance with the given headers and the given close flag,
|
||||
* the given unidirectional flag, the given associated stream, and with the given priority.</p>
|
||||
*
|
||||
* @param headers the {@link Headers}
|
||||
* @param close the value of the close flag
|
||||
* @param unidirectional the value of the unidirectional flag
|
||||
* @param associatedStreamId the associated stream id
|
||||
* @param priority the priority
|
||||
*/
|
||||
public SynInfo(Headers headers, boolean close, boolean unidirectional, int associatedStreamId, byte priority)
|
||||
{
|
||||
this.close = close;
|
||||
|
@ -46,34 +78,54 @@ public class SynInfo
|
|||
this.headers = headers;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the value of the close flag
|
||||
*/
|
||||
public boolean isClose()
|
||||
{
|
||||
return close;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the value of the unidirectional flag
|
||||
*/
|
||||
public boolean isUnidirectional()
|
||||
{
|
||||
return unidirectional;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the associated stream id
|
||||
*/
|
||||
public int getAssociatedStreamId()
|
||||
{
|
||||
return associatedStreamId;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the priority
|
||||
*/
|
||||
public byte getPriority()
|
||||
{
|
||||
return priority;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the {@link Headers}
|
||||
*/
|
||||
public Headers getHeaders()
|
||||
{
|
||||
return headers;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the close and unidirectional flags as integer
|
||||
* @see #FLAG_CLOSE
|
||||
* @see #FLAG_UNIDIRECTIONAL
|
||||
*/
|
||||
public byte getFlags()
|
||||
{
|
||||
byte flags = isClose() ? FLAG_FIN : 0;
|
||||
byte flags = isClose() ? FLAG_CLOSE : 0;
|
||||
flags += isUnidirectional() ? FLAG_UNIDIRECTIONAL : 0;
|
||||
return flags;
|
||||
}
|
||||
|
|
|
@ -19,10 +19,25 @@ package org.eclipse.jetty.spdy.api.server;
|
|||
import org.eclipse.jetty.spdy.api.Session;
|
||||
import org.eclipse.jetty.spdy.api.SessionFrameListener;
|
||||
|
||||
/**
|
||||
* <p>Specific, server-side, {@link SessionFrameListener}.</p>
|
||||
* <p>In addition to {@link SessionFrameListener}, this listener adds method
|
||||
* {@link #onConnect(Session)} that is called when a client first connects to the
|
||||
* server and may be used by a server-side application to send a SETTINGS frame
|
||||
* to configure the connection before the client can open any stream.</p>
|
||||
*/
|
||||
public interface ServerSessionFrameListener extends SessionFrameListener
|
||||
{
|
||||
/**
|
||||
* <p>Callback invoked when a client opens a connection.</p>
|
||||
*
|
||||
* @param session the session
|
||||
*/
|
||||
public void onConnect(Session session);
|
||||
|
||||
/**
|
||||
* <p>Empty implementation of {@link ServerSessionFrameListener}</p>
|
||||
*/
|
||||
public static class Adapter extends SessionFrameListener.Adapter implements ServerSessionFrameListener
|
||||
{
|
||||
@Override
|
||||
|
|
|
@ -50,7 +50,7 @@ public class DataFrame
|
|||
|
||||
public boolean isClose()
|
||||
{
|
||||
return (flags & DataInfo.FLAG_FIN) == DataInfo.FLAG_FIN;
|
||||
return (flags & DataInfo.FLAG_CLOSE) == DataInfo.FLAG_CLOSE;
|
||||
}
|
||||
|
||||
public boolean isCompress()
|
||||
|
|
|
@ -60,7 +60,7 @@ public class HeadersFrame extends ControlFrame
|
|||
|
||||
public boolean isClose()
|
||||
{
|
||||
return (getFlags() & HeadersInfo.FLAG_FIN) == HeadersInfo.FLAG_FIN;
|
||||
return (getFlags() & HeadersInfo.FLAG_CLOSE) == HeadersInfo.FLAG_CLOSE;
|
||||
}
|
||||
|
||||
public boolean isResetCompression()
|
||||
|
|
|
@ -43,7 +43,7 @@ public class SynReplyFrame extends ControlFrame
|
|||
|
||||
public boolean isClose()
|
||||
{
|
||||
return (getFlags() & ReplyInfo.FLAG_FIN) == ReplyInfo.FLAG_FIN;
|
||||
return (getFlags() & ReplyInfo.FLAG_CLOSE) == ReplyInfo.FLAG_CLOSE;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -57,7 +57,7 @@ public class SynStreamFrame extends ControlFrame
|
|||
|
||||
public boolean isClose()
|
||||
{
|
||||
return (getFlags() & SynInfo.FLAG_FIN) == SynInfo.FLAG_FIN;
|
||||
return (getFlags() & SynInfo.FLAG_CLOSE) == SynInfo.FLAG_CLOSE;
|
||||
}
|
||||
|
||||
public boolean isUnidirectional()
|
||||
|
|
|
@ -28,14 +28,14 @@ public class DataFrameGenerator
|
|||
ByteBuffer buffer = ByteBuffer.allocateDirect(DataFrame.HEADER_LENGTH + windowSize);
|
||||
buffer.position(DataFrame.HEADER_LENGTH);
|
||||
// Guaranteed to always be >= 0
|
||||
int read = dataInfo.getBytes(buffer);
|
||||
int read = dataInfo.getContent(buffer);
|
||||
|
||||
buffer.putInt(0, streamId & 0x7F_FF_FF_FF);
|
||||
buffer.putInt(4, read & 0x00_FF_FF_FF);
|
||||
|
||||
// TODO: compression can be done here, as long as we have one DataFrameGenerator per stream
|
||||
// since the compression context for data is per-stream, without dictionary
|
||||
byte flags = dataInfo.isConsumed() && dataInfo.isClose() ? DataInfo.FLAG_FIN : 0;
|
||||
byte flags = dataInfo.isConsumed() && dataInfo.isClose() ? DataInfo.FLAG_CLOSE : 0;
|
||||
buffer.put(4, flags);
|
||||
|
||||
buffer.flip();
|
||||
|
|
|
@ -40,8 +40,8 @@ public class HeadersBlockGenerator
|
|||
{
|
||||
// TODO: ByteArrayOutputStream is quite inefficient, but grows on demand; optimize using ByteBuffer ?
|
||||
Charset iso1 = Charset.forName("ISO-8859-1");
|
||||
ByteArrayOutputStream buffer = new ByteArrayOutputStream(headers.getSize() * 64);
|
||||
writeCount(version, buffer, headers.getSize());
|
||||
ByteArrayOutputStream buffer = new ByteArrayOutputStream(headers.size() * 64);
|
||||
writeCount(version, buffer, headers.size());
|
||||
for (Headers.Header header : headers)
|
||||
{
|
||||
String name = header.name();
|
||||
|
|
|
@ -80,7 +80,7 @@ public class HeadersBodyParser extends ControlFrameBodyParser
|
|||
if (headersBlockParser.parse(version, length, buffer))
|
||||
{
|
||||
byte flags = controlFrameParser.getFlags();
|
||||
if (flags != 0 && flags != HeadersInfo.FLAG_FIN && flags != HeadersInfo.FLAG_RESET_COMPRESSION)
|
||||
if (flags != 0 && flags != HeadersInfo.FLAG_CLOSE && flags != HeadersInfo.FLAG_RESET_COMPRESSION)
|
||||
throw new IllegalArgumentException("Invalid flag " + flags + " for frame " + ControlFrameType.HEADERS);
|
||||
|
||||
HeadersFrame frame = new HeadersFrame(version, flags, streamId, new Headers(headers, true));
|
||||
|
|
|
@ -120,7 +120,7 @@ public class SynReplyBodyParser extends ControlFrameBodyParser
|
|||
if (headersBlockParser.parse(version, length, buffer))
|
||||
{
|
||||
byte flags = controlFrameParser.getFlags();
|
||||
if (flags != 0 && flags != ReplyInfo.FLAG_FIN)
|
||||
if (flags != 0 && flags != ReplyInfo.FLAG_CLOSE)
|
||||
throw new IllegalArgumentException("Invalid flag " + flags + " for frame " + ControlFrameType.SYN_REPLY);
|
||||
|
||||
SynReplyFrame frame = new SynReplyFrame(version, flags, streamId, new Headers(headers, true));
|
||||
|
|
|
@ -126,7 +126,7 @@ public class SynStreamBodyParser extends ControlFrameBodyParser
|
|||
{
|
||||
byte flags = controlFrameParser.getFlags();
|
||||
// TODO: can it be both FIN and UNIDIRECTIONAL ?
|
||||
if (flags != 0 && flags != SynInfo.FLAG_FIN && flags != SynInfo.FLAG_UNIDIRECTIONAL)
|
||||
if (flags != 0 && flags != SynInfo.FLAG_CLOSE && flags != SynInfo.FLAG_UNIDIRECTIONAL)
|
||||
throw new IllegalArgumentException("Invalid flag " + flags + " for frame " + ControlFrameType.SYN_STREAM);
|
||||
|
||||
SynStreamFrame frame = new SynStreamFrame(version, flags, streamId, associatedStreamId, priority, new Headers(headers, true));
|
||||
|
|
|
@ -37,7 +37,7 @@ public class ServerUsageTest
|
|||
|
||||
// Get the http response, fill headers and data
|
||||
Headers replyHeaders = new Headers();
|
||||
replyHeaders.put("host", synHeaders.get("host"));
|
||||
replyHeaders.put(synHeaders.get("host"));
|
||||
// Sends a reply
|
||||
stream.reply(new ReplyInfo(replyHeaders, false));
|
||||
|
||||
|
|
|
@ -58,7 +58,7 @@ public class DataGenerateParseTest
|
|||
|
||||
Assert.assertNotNull(frame2);
|
||||
Assert.assertEquals(streamId, frame2.getStreamId());
|
||||
Assert.assertEquals(DataInfo.FLAG_FIN, frame2.getFlags());
|
||||
Assert.assertEquals(DataInfo.FLAG_CLOSE, frame2.getFlags());
|
||||
Assert.assertEquals(length, frame2.getLength());
|
||||
Assert.assertEquals(length, listener.getData().remaining());
|
||||
}
|
||||
|
@ -84,7 +84,7 @@ public class DataGenerateParseTest
|
|||
|
||||
Assert.assertNotNull(frame2);
|
||||
Assert.assertEquals(streamId, frame2.getStreamId());
|
||||
Assert.assertEquals(DataInfo.FLAG_FIN, frame2.getFlags());
|
||||
Assert.assertEquals(DataInfo.FLAG_CLOSE, frame2.getFlags());
|
||||
Assert.assertEquals(length, frame2.getLength());
|
||||
Assert.assertEquals(length, listener.getData().remaining());
|
||||
}
|
||||
|
|
|
@ -32,7 +32,7 @@ public class SynReplyGenerateParseTest
|
|||
@Test
|
||||
public void testGenerateParse() throws Exception
|
||||
{
|
||||
byte flags = ReplyInfo.FLAG_FIN;
|
||||
byte flags = ReplyInfo.FLAG_CLOSE;
|
||||
int streamId = 13;
|
||||
Headers headers = new Headers();
|
||||
headers.put("a", "b");
|
||||
|
@ -60,7 +60,7 @@ public class SynReplyGenerateParseTest
|
|||
@Test
|
||||
public void testGenerateParseOneByteAtATime() throws Exception
|
||||
{
|
||||
byte flags = ReplyInfo.FLAG_FIN;
|
||||
byte flags = ReplyInfo.FLAG_CLOSE;
|
||||
int streamId = 13;
|
||||
Headers headers = new Headers();
|
||||
headers.put("a", "b");
|
||||
|
|
|
@ -32,7 +32,7 @@ public class SynStreamGenerateParseTest
|
|||
@Test
|
||||
public void testGenerateParse() throws Exception
|
||||
{
|
||||
byte flags = SynInfo.FLAG_FIN;
|
||||
byte flags = SynInfo.FLAG_CLOSE;
|
||||
int streamId = 13;
|
||||
int associatedStreamId = 11;
|
||||
byte priority = 3;
|
||||
|
@ -65,7 +65,7 @@ public class SynStreamGenerateParseTest
|
|||
@Test
|
||||
public void testGenerateParseOneByteAtATime() throws Exception
|
||||
{
|
||||
byte flags = SynInfo.FLAG_FIN;
|
||||
byte flags = SynInfo.FLAG_CLOSE;
|
||||
int streamId = 13;
|
||||
int associatedStreamId = 11;
|
||||
byte priority = 3;
|
||||
|
|
|
@ -592,7 +592,7 @@ public class ServerHTTPSPDYTest
|
|||
@Override
|
||||
public void onData(Stream stream, DataInfo dataInfo)
|
||||
{
|
||||
contentBytes.addAndGet(dataInfo.getBytesCount());
|
||||
contentBytes.addAndGet(dataInfo.getContentLength());
|
||||
if (dataInfo.isClose())
|
||||
{
|
||||
Assert.assertEquals(data.length, contentBytes.get());
|
||||
|
@ -649,7 +649,7 @@ public class ServerHTTPSPDYTest
|
|||
@Override
|
||||
public void onData(Stream stream, DataInfo dataInfo)
|
||||
{
|
||||
contentBytes.addAndGet(dataInfo.getBytesCount());
|
||||
contentBytes.addAndGet(dataInfo.getContentLength());
|
||||
if (dataInfo.isClose())
|
||||
{
|
||||
Assert.assertEquals(2 * data.length, contentBytes.get());
|
||||
|
|
|
@ -134,7 +134,7 @@ public class SPDYAsyncConnection extends AbstractConnection implements AsyncConn
|
|||
catch (Exception x)
|
||||
{
|
||||
close(false);
|
||||
handler.failed(x);
|
||||
handler.failed(x, context);
|
||||
}
|
||||
finally
|
||||
{
|
||||
|
|
|
@ -123,8 +123,8 @@ public class ConcurrentSynDataReplyDataTest extends AbstractTest
|
|||
public void onData(Stream stream, DataInfo dataInfo)
|
||||
{
|
||||
Assert.assertEquals(1, latch.getCount());
|
||||
ByteBuffer buffer = ByteBuffer.allocate(dataInfo.getBytesCount());
|
||||
dataInfo.getBytes(buffer);
|
||||
ByteBuffer buffer = ByteBuffer.allocate(dataInfo.getContentLength());
|
||||
dataInfo.getContent(buffer);
|
||||
Assert.assertTrue(dataInfo.isConsumed());
|
||||
latch.countDown();
|
||||
}
|
||||
|
|
|
@ -55,7 +55,7 @@ public class FlowControlTest extends AbstractTest
|
|||
@Override
|
||||
public void onData(Stream stream, DataInfo dataInfo)
|
||||
{
|
||||
bytes.addAndGet(dataInfo.getBytesCount());
|
||||
bytes.addAndGet(dataInfo.getContentLength());
|
||||
if (dataInfo.isClose())
|
||||
dataLatch.countDown();
|
||||
}
|
||||
|
@ -88,7 +88,7 @@ public class FlowControlTest extends AbstractTest
|
|||
@Override
|
||||
public void onData(Stream stream, DataInfo dataInfo)
|
||||
{
|
||||
bytes.addAndGet(dataInfo.getBytesCount());
|
||||
bytes.addAndGet(dataInfo.getContentLength());
|
||||
if (dataInfo.isClose())
|
||||
dataLatch.countDown();
|
||||
}
|
||||
|
@ -114,7 +114,7 @@ public class FlowControlTest extends AbstractTest
|
|||
@Override
|
||||
public void onData(Stream stream, DataInfo dataInfo)
|
||||
{
|
||||
bytes.addAndGet(dataInfo.getBytesCount());
|
||||
bytes.addAndGet(dataInfo.getContentLength());
|
||||
if (dataInfo.isClose())
|
||||
dataLatch.countDown();
|
||||
}
|
||||
|
@ -146,7 +146,7 @@ public class FlowControlTest extends AbstractTest
|
|||
@Override
|
||||
public void onData(Stream stream, DataInfo dataInfo)
|
||||
{
|
||||
bytes.addAndGet(dataInfo.getBytesCount());
|
||||
bytes.addAndGet(dataInfo.getContentLength());
|
||||
if (dataInfo.isClose())
|
||||
dataLatch.countDown();
|
||||
}
|
||||
|
|
|
@ -139,7 +139,7 @@ public class SynReplyTest extends AbstractTest
|
|||
ByteBuffer buffer = ByteBuffer.allocate(2);
|
||||
while (!dataInfo.isConsumed())
|
||||
{
|
||||
dataInfo.getBytes(buffer);
|
||||
dataInfo.getContent(buffer);
|
||||
buffer.flip();
|
||||
bytes.write(buffer.array(), buffer.arrayOffset(), buffer.remaining());
|
||||
buffer.clear();
|
||||
|
@ -309,8 +309,8 @@ public class SynReplyTest extends AbstractTest
|
|||
@Override
|
||||
public void onData(Stream stream, DataInfo dataInfo)
|
||||
{
|
||||
ByteBuffer buffer = ByteBuffer.allocate(dataInfo.getBytesCount());
|
||||
dataInfo.getBytes(buffer);
|
||||
ByteBuffer buffer = ByteBuffer.allocate(dataInfo.getContentLength());
|
||||
dataInfo.getContent(buffer);
|
||||
buffer.flip();
|
||||
String data = Charset.forName("UTF-8").decode(buffer).toString();
|
||||
Assert.assertEquals(serverData, data);
|
||||
|
|
Loading…
Reference in New Issue