--- /dev/null
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+ <modelVersion>4.0.0</modelVersion>
+
+ <groupId>org.opendaylight.yangtools</groupId>
+ <artifactId>websocket-parent</artifactId>
+ <version>1.0-SNAPSHOT</version>
+ <packaging>pom</packaging>
+ <dependencyManagement>
+ <dependencies>
+ <dependency>
+ <groupId>io.netty</groupId>
+ <artifactId>netty-all</artifactId>
+ <version>4.0.10.Final</version>
+ </dependency>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-api</artifactId>
+ <version>1.7.2</version>
+ </dependency>
+ <dependency>
+ <groupId>junit</groupId>
+ <artifactId>junit</artifactId>
+ <version>4.11</version>
+ </dependency>
+ <dependency>
+ <groupId>io.netty</groupId>
+ <artifactId>netty-handler</artifactId>
+ <version>4.0.10.Final</version>
+ </dependency>
+ <dependency>
+ <groupId>io.netty</groupId>
+ <artifactId>netty-transport</artifactId>
+ <version>4.0.10.Final</version>
+ </dependency>
+ <dependency>
+ <groupId>org.opendaylight.yangtools</groupId>
+ <artifactId>websocket-server</artifactId>
+ <version>1.0-SNAPSHOT</version>
+ </dependency>
+ </dependencies>
+ </dependencyManagement>
+ <modules>
+ <module>websocket-client</module>
+ </modules>
+</project>
--- /dev/null
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>org.opendaylight.controller</groupId>
+ <artifactId>websocket-client</artifactId>
+
+ <parent>
+ <groupId>org.opendaylight.yangtools</groupId>
+ <artifactId>websocket-parent</artifactId>
+ <version>1.0-SNAPSHOT</version>
+ </parent>
+
+ <packaging>jar</packaging>
+ <version>1.0-SNAPSHOT</version>
+ <name>websocket-client</name>
+
+ <dependencies>
+ <dependency>
+ <groupId>io.netty</groupId>
+ <artifactId>netty-handler</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>io.netty</groupId>
+ <artifactId>netty-transport</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>io.netty</groupId>
+ <artifactId>netty-all</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-api</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>junit</groupId>
+ <artifactId>junit</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.opendaylight.yangtools</groupId>
+ <artifactId>websocket-server</artifactId>
+ </dependency>
+ </dependencies>
+</project>
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.yangtools.websocket.client;
+
+import io.netty.channel.Channel;
+import io.netty.channel.ChannelFuture;
+import io.netty.channel.ChannelHandlerContext;
+import io.netty.channel.ChannelPromise;
+import io.netty.channel.SimpleChannelInboundHandler;
+import io.netty.handler.codec.http.FullHttpResponse;
+import io.netty.handler.codec.http.websocketx.CloseWebSocketFrame;
+import io.netty.handler.codec.http.websocketx.PongWebSocketFrame;
+import io.netty.handler.codec.http.websocketx.TextWebSocketFrame;
+import io.netty.handler.codec.http.websocketx.WebSocketClientHandshaker;
+import io.netty.handler.codec.http.websocketx.WebSocketFrame;
+import io.netty.util.CharsetUtil;
+import org.opendaylight.controller.websocket.client.callback.ClientMessageCallback;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class WebSocketClientHandler extends SimpleChannelInboundHandler<Object> {
+
+ private static final Logger logger = LoggerFactory.getLogger(WebSocketClientHandler.class.toString());
+ private final WebSocketClientHandshaker handshaker;
+ private ChannelPromise handshakeFuture;
+ private ClientMessageCallback messageListener;
+
+
+ public WebSocketClientHandler(WebSocketClientHandshaker handshaker,ClientMessageCallback listener) {
+ this.handshaker = handshaker;
+ this.messageListener = listener;
+ }
+
+ public ChannelFuture handshakeFuture() {
+ return handshakeFuture;
+ }
+
+ @Override
+ public void handlerAdded(ChannelHandlerContext ctx) throws Exception {
+ handshakeFuture = ctx.newPromise();
+ }
+
+ @Override
+ public void channelActive(ChannelHandlerContext ctx) throws Exception {
+ handshaker.handshake(ctx.channel());
+ }
+
+ @Override
+ public void channelInactive(ChannelHandlerContext ctx) throws Exception {
+ logger.info("WebSocket Client disconnected!");
+ }
+
+ @Override
+ public void channelRead0(ChannelHandlerContext ctx, Object msg) throws Exception {
+ Channel ch = ctx.channel();
+ if (!handshaker.isHandshakeComplete()) {
+ handshaker.finishHandshake(ch, (FullHttpResponse) msg);
+ logger.info("WebSocket Client connected!");
+ handshakeFuture.setSuccess();
+ return;
+ }
+
+ if (msg instanceof FullHttpResponse) {
+ FullHttpResponse response = (FullHttpResponse) msg;
+ throw new RuntimeException("Unexpected FullHttpResponse (getStatus=" + response.getStatus() + ", content="
+ + response.content().toString(CharsetUtil.UTF_8) + ')');
+ }
+
+ messageListener.onMessageReceived(msg);
+ WebSocketFrame frame = (WebSocketFrame) msg;
+
+ if (frame instanceof TextWebSocketFrame) {
+ TextWebSocketFrame textFrame = (TextWebSocketFrame) frame;
+ logger.info("WebSocket Client received message: " + textFrame.text());
+ } else if (frame instanceof PongWebSocketFrame) {
+ logger.info("WebSocket Client received pong");
+ } else if (frame instanceof CloseWebSocketFrame) {
+ logger.info("WebSocket Client received closing");
+ ch.close();
+ }
+ }
+
+ @Override
+ public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
+ if (!handshakeFuture.isDone()) {
+ handshakeFuture.setFailure(cause);
+ }
+ ctx.close();
+ }
+}
+
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.yangtools.websocket.client;
+
+import io.netty.bootstrap.Bootstrap;
+import io.netty.buffer.Unpooled;
+import io.netty.channel.Channel;
+import io.netty.channel.ChannelInitializer;
+import io.netty.channel.ChannelPipeline;
+import io.netty.channel.EventLoopGroup;
+import io.netty.channel.nio.NioEventLoopGroup;
+import io.netty.channel.socket.SocketChannel;
+import io.netty.channel.socket.nio.NioSocketChannel;
+import io.netty.handler.codec.http.HttpClientCodec;
+import io.netty.handler.codec.http.HttpObjectAggregator;
+import io.netty.handler.codec.http.websocketx.CloseWebSocketFrame;
+import io.netty.handler.codec.http.websocketx.PingWebSocketFrame;
+import io.netty.handler.codec.http.websocketx.TextWebSocketFrame;
+import io.netty.handler.codec.http.websocketx.WebSocketClientHandshakerFactory;
+import io.netty.handler.codec.http.websocketx.WebSocketVersion;
+import java.net.URI;
+import org.opendaylight.controller.websocket.client.callback.ClientMessageCallback;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class WebSocketIClient {
+
+ private final URI uri;
+ private Bootstrap bootstrap = new Bootstrap();;
+ private final WebSocketClientHandler clientHandler;
+ private static final Logger logger = LoggerFactory.getLogger(WebSocketIClient.class);
+ private Channel clientChannel;
+ private final EventLoopGroup group = new NioEventLoopGroup();
+
+
+ public WebSocketIClient(URI uri,ClientMessageCallback clientMessageCallback) {
+ this.uri = uri;
+ clientHandler = new WebSocketClientHandler(
+ WebSocketClientHandshakerFactory.newHandshaker(
+ uri, WebSocketVersion.V13, null, false,null),clientMessageCallback); // last null could be replaced with DefaultHttpHeaders
+ initialize();
+ }
+ private void initialize(){
+
+ String protocol = uri.getScheme();
+ if (!"ws".equals(protocol)) {
+ throw new IllegalArgumentException("Unsupported protocol: " + protocol);
+ }
+
+ bootstrap.group(group)
+ .channel(NioSocketChannel.class)
+ .handler(new ChannelInitializer<SocketChannel>() {
+ @Override
+ public void initChannel(SocketChannel ch) throws Exception {
+ ChannelPipeline pipeline = ch.pipeline();
+ pipeline.addLast("http-codec", new HttpClientCodec());
+ pipeline.addLast("aggregator", new HttpObjectAggregator(8192));
+ pipeline.addLast("ws-handler", clientHandler);
+ }
+ });
+ }
+ public void connect() throws InterruptedException{
+ clientChannel = bootstrap.connect(uri.getHost(), uri.getPort()).sync().channel();
+ clientHandler.handshakeFuture().sync();
+ }
+
+ public void writeAndFlush(String message){
+ clientChannel.writeAndFlush(new TextWebSocketFrame(message));
+ }
+ public void writeAndFlush(Object message){
+ clientChannel.writeAndFlush(message);
+ }
+
+ public void ping(){
+ clientChannel.writeAndFlush(new PingWebSocketFrame(Unpooled.copiedBuffer(new byte[]{1, 2, 3, 4, 5, 6})));
+ }
+
+ public void close() throws InterruptedException {
+ clientChannel.writeAndFlush(new CloseWebSocketFrame());
+
+ // WebSocketClientHandler will close the connection when the server
+ // responds to the CloseWebSocketFrame.
+ clientChannel.closeFuture().sync();
+ group.shutdownGracefully();
+ }
+
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.controller.websocket.client.callback;
+
+public interface ClientMessageCallback {
+
+ public void onMessageReceived(Object message);
+}
--- /dev/null
+/*
+ * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ * and is available at http://www.eclipse.org/legal/epl-v10.html
+ */
+package org.opendaylight.yangtools.websocket;
+
+import io.netty.handler.codec.http.websocketx.CloseWebSocketFrame;
+import java.net.URI;
+import java.net.URISyntaxException;
+import org.junit.Before;
+import org.junit.Test;
+import org.opendaylight.yangtools.websocket.client.WebSocketIClient;
+import org.opendaylight.yangtools.websocket.server.WebSocketServer;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class WebSocketClientTest {
+ private static final Logger logger = LoggerFactory.getLogger(WebSocketClientTest.class.toString());
+ private static final String MESSAGE = "Take me to your leader!";
+ private static final int port = 8080;
+ private Thread webSocketServerThread;
+
+
+ @Before
+ public void startWebSocketServer(){
+ try {
+ WebSocketServer webSocketServer = new WebSocketServer(port);
+ webSocketServerThread = new Thread(webSocketServer);
+ webSocketServerThread.setDaemon(false);
+ webSocketServerThread.start();
+ } catch (Exception e) {
+ logger.trace("Error starting websocket server");
+ }
+ }
+ @Test
+ public void connectAndSendData(){
+
+ URI uri = null;
+ try {
+ uri = new URI("ws://localhost:8080/websocket");
+ ClientMessageCallback messageCallback = new ClientMessageCallback();
+ WebSocketIClient wsClient = new WebSocketIClient(uri,messageCallback);
+ try {
+ wsClient.connect();
+ wsClient.writeAndFlush(MESSAGE);
+ wsClient.writeAndFlush(new CloseWebSocketFrame());
+ webSocketServerThread.interrupt();
+ } catch (InterruptedException e) {
+ logger.info("WebSocket client couldn't connect to : "+uri);
+ }
+ } catch (URISyntaxException e) {
+ logger.info("There is an error in URL sytnax {}",e);
+ }
+ }
+
+ private class ClientMessageCallback implements org.opendaylight.controller.websocket.client.callback.ClientMessageCallback {
+ @Override
+ public void onMessageReceived(Object message) {
+ logger.info("received message {}",message);
+ System.out.println("received message : " + message);
+ }
+ }
+}
--- /dev/null
+/*
+ * Copyright 2012 The Netty Project
+ *
+ * The Netty Project licenses this file to you under the Apache License,
+ * version 2.0 (the "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ */
+package org.opendaylight.yangtools.websocket.server;
+
+import io.netty.bootstrap.ServerBootstrap;
+import io.netty.channel.Channel;
+import io.netty.channel.EventLoopGroup;
+import io.netty.channel.nio.NioEventLoopGroup;
+import io.netty.channel.socket.nio.NioServerSocketChannel;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * A HTTP server which serves Web Socket requests at:
+ *
+ * http://localhost:8080/websocket
+ *
+ * Open your browser at http://localhost:8080/, then the demo page will be loaded and a Web Socket connection will be
+ * made automatically.
+ *
+ * This server illustrates support for the different web socket specification versions and will work with:
+ *
+ * <ul>
+ * <li>Safari 5+ (draft-ietf-hybi-thewebsocketprotocol-00)
+ * <li>Chrome 6-13 (draft-ietf-hybi-thewebsocketprotocol-00)
+ * <li>Chrome 14+ (draft-ietf-hybi-thewebsocketprotocol-10)
+ * <li>Chrome 16+ (RFC 6455 aka draft-ietf-hybi-thewebsocketprotocol-17)
+ * <li>Firefox 7+ (draft-ietf-hybi-thewebsocketprotocol-10)
+ * <li>Firefox 11+ (RFC 6455 aka draft-ietf-hybi-thewebsocketprotocol-17)
+ * </ul>
+ */
+public class WebSocketServer implements Runnable {
+
+ private final int port;
+ private final ServerBootstrap bootstrap = new ServerBootstrap();
+ private final EventLoopGroup bossGroup = new NioEventLoopGroup();
+ private final EventLoopGroup workerGroup = new NioEventLoopGroup();
+ private static final Logger logger = LoggerFactory.getLogger(WebSocketServer.class.toString());
+
+ public WebSocketServer(int port) {
+ this.port = port;
+ }
+
+ public void run(){
+ try {
+ startServer();
+ } catch (Exception e) {
+ logger.info("Exception occured while starting webSocket server {}",e);
+ }
+ }
+ public void startServer() throws Exception {
+ try {
+ bootstrap.group(bossGroup, workerGroup)
+ .channel(NioServerSocketChannel.class)
+ .childHandler(new WebSocketServerInitializer());
+
+ Channel ch = bootstrap.bind(port).sync().channel();
+ logger.info("Web socket server started at port " + port + '.');
+ logger.info("Open your browser and navigate to http://localhost:" + port + '/');
+
+ ch.closeFuture().sync();
+ } finally {
+ bossGroup.shutdownGracefully();
+ workerGroup.shutdownGracefully();
+ }
+ }
+
+
+}
--- /dev/null
+/*
+ * Copyright 2012 The Netty Project
+ *
+ * The Netty Project licenses this file to you under the Apache License,
+ * version 2.0 (the "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ */
+package org.opendaylight.yangtools.websocket.server;
+
+import io.netty.buffer.ByteBuf;
+import io.netty.buffer.Unpooled;
+import io.netty.channel.ChannelFuture;
+import io.netty.channel.ChannelFutureListener;
+import io.netty.channel.ChannelHandlerContext;
+import io.netty.channel.SimpleChannelInboundHandler;
+import io.netty.handler.codec.http.DefaultFullHttpResponse;
+import io.netty.handler.codec.http.FullHttpRequest;
+import io.netty.handler.codec.http.FullHttpResponse;
+import io.netty.handler.codec.http.websocketx.CloseWebSocketFrame;
+import io.netty.handler.codec.http.websocketx.PingWebSocketFrame;
+import io.netty.handler.codec.http.websocketx.PongWebSocketFrame;
+import io.netty.handler.codec.http.websocketx.TextWebSocketFrame;
+import io.netty.handler.codec.http.websocketx.WebSocketFrame;
+import io.netty.handler.codec.http.websocketx.WebSocketServerHandshaker;
+import io.netty.handler.codec.http.websocketx.WebSocketServerHandshakerFactory;
+import io.netty.util.CharsetUtil;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import static io.netty.handler.codec.http.HttpHeaders.Names.HOST;
+import static io.netty.handler.codec.http.HttpHeaders.isKeepAlive;
+import static io.netty.handler.codec.http.HttpHeaders.setContentLength;
+import static io.netty.handler.codec.http.HttpMethod.GET;
+import static io.netty.handler.codec.http.HttpResponseStatus.BAD_REQUEST;
+import static io.netty.handler.codec.http.HttpResponseStatus.FORBIDDEN;
+import static io.netty.handler.codec.http.HttpVersion.HTTP_1_1;
+
+/**
+ * Handles handshakes and messages
+ */
+public class WebSocketServerHandler extends SimpleChannelInboundHandler<Object> {
+ private static final Logger logger = LoggerFactory.getLogger(WebSocketServerHandler.class.getName());
+
+ private static final String WEBSOCKET_PATH = "/websocket";
+
+ private WebSocketServerHandshaker handshaker;
+
+ @Override
+ public void channelRead0(ChannelHandlerContext ctx, Object msg) throws Exception {
+ if (msg instanceof FullHttpRequest) {
+ handleHttpRequest(ctx, (FullHttpRequest) msg);
+ } else if (msg instanceof WebSocketFrame) {
+ handleWebSocketFrame(ctx, (WebSocketFrame) msg);
+ }
+ }
+
+ @Override
+ public void channelReadComplete(ChannelHandlerContext ctx) throws Exception {
+ ctx.flush();
+ }
+
+ private void handleHttpRequest(ChannelHandlerContext ctx, FullHttpRequest req) throws Exception {
+ // Handle a bad request.
+ if (!req.getDecoderResult().isSuccess()) {
+ sendHttpResponse(ctx, req, new DefaultFullHttpResponse(HTTP_1_1, BAD_REQUEST));
+ return;
+ }
+
+ // Allow only GET methods.
+ if (req.getMethod() != GET) {
+ sendHttpResponse(ctx, req, new DefaultFullHttpResponse(HTTP_1_1, FORBIDDEN));
+ return;
+ }
+
+
+ // Handshake
+ WebSocketServerHandshakerFactory wsFactory = new WebSocketServerHandshakerFactory(
+ getWebSocketLocation(req), null, false);
+ handshaker = wsFactory.newHandshaker(req);
+ if (handshaker == null) {
+ WebSocketServerHandshakerFactory.sendUnsupportedWebSocketVersionResponse(ctx.channel());
+ } else {
+ handshaker.handshake(ctx.channel(), req);
+ }
+ }
+
+ private void handleWebSocketFrame(ChannelHandlerContext ctx, WebSocketFrame frame) {
+
+ // Check for closing frame
+ if (frame instanceof CloseWebSocketFrame) {
+ handshaker.close(ctx.channel(), (CloseWebSocketFrame) frame.retain());
+ return;
+ }
+ if (frame instanceof PingWebSocketFrame) {
+ ctx.channel().write(new PongWebSocketFrame(frame.content().retain()));
+ return;
+ }
+ if (!(frame instanceof TextWebSocketFrame)) {
+ throw new UnsupportedOperationException(String.format("%s frame types not supported", frame.getClass()
+ .getName()));
+ }
+
+ // Send the uppercase string back.
+ String request = ((TextWebSocketFrame) frame).text();
+ logger.debug(String.format("%s received %s", ctx.channel(), request));
+ ctx.channel().write(new TextWebSocketFrame(request.toUpperCase()));
+ }
+
+ private static void sendHttpResponse(
+ ChannelHandlerContext ctx, FullHttpRequest req, FullHttpResponse res) {
+ // Generate an error page if response getStatus code is not OK (200).
+ if (res.getStatus().code() != 200) {
+ ByteBuf buf = Unpooled.copiedBuffer(res.getStatus().toString(), CharsetUtil.UTF_8);
+ res.content().writeBytes(buf);
+ buf.release();
+ setContentLength(res, res.content().readableBytes());
+ }
+
+ // Send the response and close the connection if necessary.
+ ChannelFuture f = ctx.channel().writeAndFlush(res);
+ if (!isKeepAlive(req) || res.getStatus().code() != 200) {
+ f.addListener(ChannelFutureListener.CLOSE);
+ }
+ }
+
+ @Override
+ public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
+ logger.info("Exception caught {}",cause);
+ ctx.close();
+ }
+
+ private static String getWebSocketLocation(FullHttpRequest req) {
+ return "ws://" + req.headers().get(HOST) + WEBSOCKET_PATH;
+ }
+
+
+}
--- /dev/null
+/*
+ * Copyright 2012 The Netty Project
+ *
+ * The Netty Project licenses this file to you under the Apache License,
+ * version 2.0 (the "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ */
+package org.opendaylight.yangtools.websocket.server;
+
+import io.netty.channel.ChannelInitializer;
+import io.netty.channel.ChannelPipeline;
+import io.netty.channel.socket.SocketChannel;
+import io.netty.handler.codec.http.HttpObjectAggregator;
+import io.netty.handler.codec.http.HttpServerCodec;
+import org.opendaylight.yangtools.websocket.server.WebSocketServerHandler;
+
+/**
+ */
+public class WebSocketServerInitializer extends ChannelInitializer<SocketChannel> {
+ @Override
+ public void initChannel(SocketChannel ch) throws Exception {
+ ChannelPipeline pipeline = ch.pipeline();
+ pipeline.addLast("codec-http", new HttpServerCodec());
+ pipeline.addLast("aggregator", new HttpObjectAggregator(65536));
+ pipeline.addLast("handler", new WebSocketServerHandler());
+ }
+}
--- /dev/null
+<configuration scan="true">
+
+ <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
+ <encoder>
+ <pattern>%date{"yyyy-MM-dd HH:mm:ss.SSS z"} [%thread] %-5level %logger{36} - %msg%n</pattern>
+ </encoder>
+ </appender>
+
+ <logger name="org.opendaylight.controller" level="DEBUG"/>
+
+ <root level="error">
+ <appender-ref ref="STDOUT" />
+ </root>
+
+</configuration>