Collaborating with Jesse on WebSocket API

This commit is contained in:
Joakim Erdfelt 2012-06-22 06:32:21 -07:00
parent 1a73c74d96
commit 853905a7c0
2 changed files with 126 additions and 197 deletions

View File

@ -1,5 +1,5 @@
/******************************************************************************* /*******************************************************************************
* Copyright (c) 2011 Intalio, Inc. * Copyright (c) 2011 Mort Bay Consulting Pty. Ltd.
* ====================================================================== * ======================================================================
* All rights reserved. This program and the accompanying materials * All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0 * are made available under the terms of the Eclipse Public License v1.0
@ -13,23 +13,13 @@
* *
* You may elect to redistribute this code under either of these licenses. * You may elect to redistribute this code under either of these licenses.
*******************************************************************************/ *******************************************************************************/
// ========================================================================
// Copyright (c) 2010 Mort Bay Consulting Pty. Ltd.
// ------------------------------------------------------------------------
// All rights reserved. This program and the accompanying materials
// are made available under the terms of the Eclipse Public License v1.0
// and Apache License v2.0 which accompanies this distribution.
// The Eclipse Public License is available at
// http://www.eclipse.org/legal/epl-v10.html
// The Apache License v2.0 is available at
// http://www.opensource.org/licenses/apache2.0.php
// You may elect to redistribute this code under either of these licenses.
// ========================================================================
package org.eclipse.jetty.websocket; package org.eclipse.jetty.websocket;
import java.io.IOException; import java.io.IOException;
import org.eclipse.jetty.websocket.api.WebSocketPolicy;
/** /**
* WebSocket Interface. * WebSocket Interface.
* <p> * <p>
@ -37,31 +27,50 @@ import java.io.IOException;
* The Interface has several nested interfaces, for each type of message that may be received. * The Interface has several nested interfaces, for each type of message that may be received.
*/ */
public interface WebSocket public interface WebSocket
{ {
/** /**
* Called when a new websocket connection is accepted. * A Connection interface is passed to a WebSocket instance via the {@link WebSocket#onOpen(Connection)} to give the application access to the specifics of
* @param connection The Connection object to use to send messages. * the current connection. This includes methods for sending frames and messages as well as methods for interpreting the flags and opcodes of the
* connection.
*/ */
void onOpen(Connection connection); public interface Connection
/**
* Called when an established websocket connection closes
* @param closeCode
* @param message
*/
void onClose(int closeCode, String message);
/**
* A nested WebSocket interface for receiving text messages
*/
interface OnTextMessage extends WebSocket
{ {
/** /**
* Called with a complete text message when all fragments have been received. * Close the connection with normal close code.
* The maximum size of text message that may be aggregated from multiple frames is set with {@link Connection#setMaxTextMessageSize(int)}.
* @param data The message
*/ */
void onMessage(String data); void close();
/** Close the connection with specific closeCode and message.
* @param closeCode The close code to send, or -1 for no close code
* @param message The message to send or null for no message
*/
void close(int closeCode,String message);
/**
* Enqueue a text message to be sent.
* <p>
* It is possible that the message might be split up and fragmented to satisfy
* policies in place on the websocket.
*
* @param message the message text to send.
* @throws IOException
*/
void enqueTextMessage(String message) throws IOException;
/**
* Get the websocket policy in use for this connection.
* @return connection specific websocket policy.
*/
WebSocketPolicy getPolicy();
/**
* Get the active scheme. "ws" (websocket) or "wss" (websocket secure)
*
* @return the active protocol scheme
*/
String getProtocol();
boolean isOpen();
} }
/** /**
@ -78,13 +87,13 @@ public interface WebSocket
*/ */
void onMessage(byte[] data, int offset, int length); void onMessage(byte[] data, int offset, int length);
} }
/** /**
* A nested WebSocket interface for receiving control messages * A nested WebSocket interface for receiving control messages
*/ */
interface OnControl extends WebSocket interface OnControl extends WebSocket
{ {
/** /**
* Called when a control message has been received. * Called when a control message has been received.
* @param controlCode * @param controlCode
* @param data * @param data
@ -94,7 +103,7 @@ public interface WebSocket
*/ */
boolean onControl(byte controlCode,byte[] data, int offset, int length); boolean onControl(byte controlCode,byte[] data, int offset, int length);
} }
/** /**
* A nested WebSocket interface for receiving any websocket frame * A nested WebSocket interface for receiving any websocket frame
*/ */
@ -110,176 +119,33 @@ public interface WebSocket
* @return true if this call has completely handled the frame and no further processing is needed (including aggregation and/or message delivery) * @return true if this call has completely handled the frame and no further processing is needed (including aggregation and/or message delivery)
*/ */
boolean onFrame(byte flags,byte opcode,byte[] data, int offset, int length); boolean onFrame(byte flags,byte opcode,byte[] data, int offset, int length);
void onHandshake(FrameConnection connection); void onHandshake(FrameConnection connection);
} }
/** /**
* A Connection interface is passed to a WebSocket instance via the {@link WebSocket#onOpen(Connection)} to * A nested WebSocket interface for receiving text messages
* give the application access to the specifics of the current connection. This includes methods
* for sending frames and messages as well as methods for interpreting the flags and opcodes of the connection.
*/ */
public interface Connection interface OnTextMessage extends WebSocket
{ {
String getProtocol();
void sendMessage(String data) throws IOException;
void sendMessage(byte[] data, int offset, int length) throws IOException;
/** /**
* @deprecated Use {@link #close()} * Called with a complete text message when all fragments have been received.
* The maximum size of text message that may be aggregated from multiple frames is set with {@link Connection#setMaxTextMessageSize(int)}.
* @param data The message
*/ */
void disconnect(); void onMessage(String data);
/**
* Close the connection with normal close code.
*/
void close();
/** Close the connection with specific closeCode and message.
* @param closeCode The close code to send, or -1 for no close code
* @param message The message to send or null for no message
*/
void close(int closeCode,String message);
boolean isOpen();
/**
* @param ms The time in ms that the connection can be idle before closing
*/
void setMaxIdleTime(int ms);
/**
* @param size size<0 No aggregation of frames to messages, >=0 max size of text frame aggregation buffer in characters
*/
void setMaxTextMessageSize(int size);
/**
* @param size size<0 no aggregation of binary frames, >=0 size of binary frame aggregation buffer
*/
void setMaxBinaryMessageSize(int size);
/**
* @return The time in ms that the connection can be idle before closing
*/
int getMaxIdleTime();
/**
* Size in characters of the maximum text message to be received
* @return size <0 No aggregation of frames to messages, >=0 max size of text frame aggregation buffer in characters
*/
int getMaxTextMessageSize();
/**
* Size in bytes of the maximum binary message to be received
* @return size <0 no aggregation of binary frames, >=0 size of binary frame aggregation buffer
*/
int getMaxBinaryMessageSize();
} }
/** /**
* Frame Level Connection * Called when an established websocket connection closes
* <p>The Connection interface at the level of sending/receiving frames rather than messages. * @param closeCode
* Also contains methods to decode/generate flags and opcodes without using constants, so that * @param message
* code can be written to work with multiple drafts of the protocol.
*
*/ */
public interface FrameConnection extends Connection void onClose(int closeCode, String message);
{
/**
* @return The opcode of a binary message
*/
byte binaryOpcode();
/**
* @return The opcode of a text message
*/
byte textOpcode();
/**
* @return The opcode of a continuation frame
*/
byte continuationOpcode();
/**
* @return Mask for the FIN bit.
*/
byte finMask();
/** Set if frames larger than the frame buffer are handled with local fragmentations
* @param allowFragmentation
*/
void setAllowFrameFragmentation(boolean allowFragmentation);
/** /**
* @param flags The flags bytes of a frame * Called when a new websocket connection is accepted.
* @return True of the flags indicate a final frame. * @param connection The Connection object to use to send messages.
*/ */
boolean isMessageComplete(byte flags); void onOpen(Connection connection);
/**
* @param opcode
* @return True if the opcode is for a control frame
*/
boolean isControl(byte opcode);
/**
* @param opcode
* @return True if the opcode is for a text frame
*/
boolean isText(byte opcode);
/**
* @param opcode
* @return True if the opcode is for a binary frame
*/
boolean isBinary(byte opcode);
/**
* @param opcode
* @return True if the opcode is for a continuation frame
*/
boolean isContinuation(byte opcode);
/**
* @param opcode
* @return True if the opcode is a close control
*/
boolean isClose(byte opcode);
/**
* @param opcode
* @return True if the opcode is a ping control
*/
boolean isPing(byte opcode);
/**
* @param opcode
* @return True if the opcode is a pong control
*/
boolean isPong(byte opcode);
/**
* @return True if frames larger than the frame buffer are fragmented.
*/
boolean isAllowFrameFragmentation();
/** Send a control frame
* @param control
* @param data
* @param offset
* @param length
* @throws IOException
*/
void sendControl(byte control,byte[] data, int offset, int length) throws IOException;
/** Send an arbitrary frame
* @param flags
* @param opcode
* @param data
* @param offset
* @param length
* @throws IOException
*/
void sendFrame(byte flags,byte opcode,byte[] data, int offset, int length) throws IOException;
}
} }

View File

@ -1,13 +1,76 @@
package org.eclipse.jetty.websocket.api; package org.eclipse.jetty.websocket.api;
import java.nio.ByteBuffer;
import java.util.concurrent.Future;
import org.eclipse.jetty.websocket.frames.BaseFrame;
import org.eclipse.jetty.websocket.frames.BinaryFrame;
import org.eclipse.jetty.websocket.frames.CloseFrame;
import org.eclipse.jetty.websocket.frames.ControlFrame;
import org.eclipse.jetty.websocket.frames.DataFrame;
import org.eclipse.jetty.websocket.frames.PingFrame;
import org.eclipse.jetty.websocket.frames.TextFrame;
/** /**
* Constants for WebSocket protocol as-defined in <a href="https://tools.ietf.org/html/rfc6455">RFC-6455</a>. * Constants for WebSocket protocol as-defined in <a href="https://tools.ietf.org/html/rfc6455">RFC-6455</a>.
*/ */
public class WebSocket public interface WebSocket
{ {
/** /**
* Per <a href="https://tools.ietf.org/html/rfc6455#section-1.3">RFC 6455, section 1.3</a> - Opening Handshake - this version is "13" * Per <a href="https://tools.ietf.org/html/rfc6455#section-1.3">RFC 6455, section 1.3</a> - Opening Handshake - this version is "13"
*/ */
public final static int VERSION = 13; public final static int VERSION = 13;
/*
* Connection
* - void terminateConnection();
* - void terminateConnection(int statusCode);
* - void terminateConnection(int statusCode, String reason);
* - FutureCallback<Void> sendFrame(BaseFrame frame)
* - FutureCallback<Void> sendText(String text)
* - FutureCallback<Void> sendBinary(ByteBuffer payload)
* - FutureCallback<Void> sendBinary(byte buf[], int offset, int len)
*
* @OnWebSocketHandshake
* public void {methodname}(Connection conn)
*
* @OnWebSocketConnect
* public void {methodname}(Connection conn)
*
* @OnWebSocketDisconnect
* public void {methodname}(Connection conn)
*
* @OnWebSocketFrame(type=CloseFrame.class)
* public void {methodname}(CloseFrame frame);
*
* @OnWebSocketText
* public void {methodname}(String text);
*
* @OnWebSocketBinary
* public void {methodname}(byte buf[], int offset, int length);
* public void {methodname}(ByteBuffer buffer);
*
* @OnWebSocketClose
* public void {methodnamne}(int statusCode, String reason);
*/
void onBinaryFrame(BinaryFrame frame);
void onClose(int statusCode, String reason);
void onCloseFrame(CloseFrame frame);
void onControlFrame(ControlFrame frame);
void onDataFrame(DataFrame frame);
void onHandshake(/* what params? */);
void onOpen();
void onTextFrame(TextFrame frame);
void sendBinary(byte buf[]);
void sendBinary(ByteBuffer buffer);
Future<Runnable> sendFrame(BaseFrame frame);
void sendPong(PingFrame frame);
void sendText(String message);
} }