json/src/main/java/net/java/html/json/doc-files/websockets.html
author Jaroslav Tulach <jaroslav.tulach@netbeans.org>
Fri, 07 Feb 2014 07:44:34 +0100
changeset 551 7ca2253fa86d
parent 365 5c93ad8c7a15
permissions -rw-r--r--
Updating copyright headers to mention current year
jtulach@293
     1
<!--
jtulach@293
     2
jaroslav@358
     3
    DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
jtulach@293
     4
jaroslav@551
     5
    Copyright 2013-2014 Oracle and/or its affiliates. All rights reserved.
jtulach@293
     6
jaroslav@358
     7
    Oracle and Java are registered trademarks of Oracle and/or its affiliates.
jaroslav@358
     8
    Other names may be trademarks of their respective owners.
jtulach@293
     9
jaroslav@358
    10
    The contents of this file are subject to the terms of either the GNU
jaroslav@358
    11
    General Public License Version 2 only ("GPL") or the Common
jaroslav@358
    12
    Development and Distribution License("CDDL") (collectively, the
jaroslav@358
    13
    "License"). You may not use this file except in compliance with the
jaroslav@358
    14
    License. You can obtain a copy of the License at
jaroslav@358
    15
    http://www.netbeans.org/cddl-gplv2.html
jaroslav@358
    16
    or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
jaroslav@358
    17
    specific language governing permissions and limitations under the
jaroslav@358
    18
    License.  When distributing the software, include this License Header
jaroslav@358
    19
    Notice in each file and include the License file at
jaroslav@358
    20
    nbbuild/licenses/CDDL-GPL-2-CP.  Oracle designates this
jaroslav@358
    21
    particular file as subject to the "Classpath" exception as provided
jaroslav@358
    22
    by Oracle in the GPL Version 2 section of the License file that
jaroslav@358
    23
    accompanied this code. If applicable, add the following below the
jaroslav@358
    24
    License Header, with the fields enclosed by brackets [] replaced by
jaroslav@358
    25
    your own identifying information:
jaroslav@358
    26
    "Portions Copyrighted [year] [name of copyright owner]"
jaroslav@358
    27
jaroslav@358
    28
    Contributor(s):
jaroslav@358
    29
jaroslav@358
    30
    The Original Software is NetBeans. The Initial Developer of the Original
jaroslav@551
    31
    Software is Oracle. Portions Copyright 2013-2014 Oracle. All Rights Reserved.
jaroslav@358
    32
jaroslav@358
    33
    If you wish your version of this file to be governed by only the CDDL
jaroslav@358
    34
    or only the GPL Version 2, indicate your decision by adding
jaroslav@358
    35
    "[Contributor] elects to include this software in this distribution
jaroslav@358
    36
    under the [CDDL or GPL Version 2] license." If you do not indicate a
jaroslav@358
    37
    single choice of license, a recipient has the option to distribute
jaroslav@358
    38
    your version of this file under either the CDDL, the GPL Version 2 or
jaroslav@358
    39
    to extend the choice of license to its licensees as provided above.
jaroslav@358
    40
    However, if you add GPL Version 2 code and therefore, elected the GPL
jaroslav@358
    41
    Version 2 license, then the option applies only if the new code is
jaroslav@358
    42
    made subject to such option by the copyright holder.
jtulach@293
    43
jtulach@293
    44
-->
jaroslav@291
    45
<!DOCTYPE html>
jaroslav@291
    46
<html>
jaroslav@291
    47
    <head>
jaroslav@291
    48
        <title>WebSockets via @OnReceive</title>
jaroslav@291
    49
        <meta charset="UTF-8">
jaroslav@291
    50
        <link rel="stylesheet" type="text/css" href="../../../../../stylesheet.css" title="Style">
jaroslav@291
    51
    </head>
jaroslav@291
    52
    <body>
jaroslav@291
    53
        <h1>Using <a href="../OnReceive.html">@OnReceive</a> to Communicate 
jaroslav@291
    54
            via WebSockets Protocol</h1>
jaroslav@291
    55
        
jaroslav@291
    56
        There is a simple, yet flexible way to communicate with a server
jaroslav@291
    57
        via <a href="http://www.w3.org/TR/websockets/">WebSockets protocol</a>.
jaroslav@291
    58
        The support can transfer any classes generated by
jaroslav@291
    59
        <a href="../Model.html">@Model</a> annotation and reuses already 
jaroslav@291
    60
        existing <a href="../OnReceive.html">@OnReceive</a> infrastructure -
jaroslav@291
    61
        just defines detailed special behavior, which is described here.
jaroslav@291
    62
        
jaroslav@291
    63
        <h3>Define JSON Class</h3>
jaroslav@291
    64
        
jaroslav@291
    65
        The first step in using <em>WebSockets</em> is to create a model classes
jaroslav@291
    66
        to encapsulate communiation with the server. For example one for
jaroslav@291
    67
        sending requests and one for receiving replies:
jaroslav@291
    68
    <pre>
jaroslav@291
    69
    <a href="../Model.html">@Model</a>(className = "Comm", properties={})
jaroslav@291
    70
    <b>final class</b> Communication {
jaroslav@291
    71
        <a href="../Model.html">@Model</a>(className = "Request", properties = {
jaroslav@291
    72
            <a href="../Property.html">@Property</a>(name = "msg", type = MsgType<b>.class</b>),
jaroslav@291
    73
            <a href="../Property.html">@Property</a>(name = "username", type = String<b>.class</b>),
jaroslav@291
    74
            <a href="../Property.html">@Property</a>(name = "password", type = String<b>.class</b>),
jaroslav@291
    75
            <a href="../Property.html">@Property</a>(name = "gameId", type = String<b>.class</b>),
jaroslav@291
    76
            <a href="../Property.html">@Property</a>(name = "color", type = Color<b>.class</b>),
jaroslav@291
    77
            <a href="../Property.html">@Property</a>(name = "from", type = String<b>.class</b>),
jaroslav@291
    78
            <a href="../Property.html">@Property</a>(name = "to", type = String<b>.class</b>),
jaroslav@291
    79
            <a href="../Property.html">@Property</a>(name = "observer", type = boolean<b>.class</b>),
jaroslav@291
    80
        })
jaroslav@291
    81
        <b>static class</b> <em>RequestModel</em> {
jaroslav@291
    82
        }
jaroslav@291
    83
jaroslav@291
    84
        <a href="../Model.html">@Model</a>(className = "Response", properties = {
jaroslav@291
    85
            <a href="../Property.html">@Property</a>(name = "msg", type = MsgType<b>.class</b>),
jaroslav@291
    86
            <a href="../Property.html">@Property</a>(name = "turn", type = Color<b>.class</b>),
jaroslav@291
    87
            <a href="../Property.html">@Property</a>(name = "color", type = Color<b>.class</b>),
jaroslav@291
    88
            <a href="../Property.html">@Property</a>(name = "gameId", type = String<b>.class</b>),
jaroslav@291
    89
            <a href="../Property.html">@Property</a>(name = "status", type = String<b>.class</b>),
jaroslav@291
    90
            <a href="../Property.html">@Property</a>(name = "moves", type = String<b>.class</b>, array = <b>true</b>),
jaroslav@291
    91
            <a href="../Property.html">@Property</a>(name = "from", type = String<b>.class</b>),
jaroslav@291
    92
            <a href="../Property.html">@Property</a>(name = "to", type = String<b>.class</b>),
jaroslav@291
    93
        })
jaroslav@291
    94
        <b>static class</b> <em>ResponseModel</em> {
jaroslav@291
    95
        }
jaroslav@291
    96
jaroslav@291
    97
        <b>enum</b> <em>MsgType</em> {
jaroslav@291
    98
            CreateGame, QueryGames, SendMove, JoinGame, UpdateGame;
jaroslav@291
    99
        }
jaroslav@291
   100
        <b>enum</b> <em>Color</em> {
jaroslav@291
   101
            W, B;
jaroslav@291
   102
        }
jaroslav@291
   103
    }            
jaroslav@291
   104
    </pre>
jaroslav@291
   105
And then it is just a matter of creating the communication end point. As
jaroslav@291
   106
usual with <a href="../OnReceive.html">@OnReceive</a> annotation one starts
jaroslav@291
   107
with defining the response handler:
jaroslav@291
   108
    <pre>
jaroslav@291
   109
    <a href="../OnReceive.html">@OnReceive</a>(
jaroslav@291
   110
        data = <em>Request</em>.<b>class</b>, 
jaroslav@291
   111
        url = "{url}", 
jaroslav@291
   112
        method = <em>"WebSocket"</em>, 
jaroslav@291
   113
        onError = "anErrorHappened"
jaroslav@291
   114
    ) 
jaroslav@291
   115
    <b>static void</b> queryServer(Comm c, Response r) {
jaroslav@291
   116
        <b>if</b> (r == null) {
jaroslav@291
   117
            // <em>connection stablished!</em>
jaroslav@291
   118
            <b>return</b>;
jaroslav@291
   119
        }
jaroslav@291
   120
        // <em>message arrived!</em>
jaroslav@291
   121
        <b>switch</b> (r.getMsg()) {
jaroslav@291
   122
            <b>case</b> CreateGame: /* do something */ <b>break</b>;
jaroslav@291
   123
            <b>case</b> QueryGames: /* do something */ <b>break</b>;
jaroslav@291
   124
            <b>case</b> SendMove: /* do something */ <b>break</b>;
jaroslav@291
   125
            <b>case</b> JoinGame: /* do something */ <b>break</b>;
jaroslav@291
   126
            <b>case</b> UpdateGame: /* do something */ <b>break</b>;
jaroslav@291
   127
        }
jaroslav@291
   128
    }
jaroslav@291
   129
    <b>static void</b> anErrorHappened(Comm c, Exception t) {
jaroslav@291
   130
        if (t == null) {
jaroslav@291
   131
            // <em>OK, connection has been closed</em>
jaroslav@291
   132
        } else {
jaroslav@291
   133
            // <em>handle the error t somehow</em>
jaroslav@291
   134
        }
jaroslav@291
   135
    }
jaroslav@291
   136
    </pre>
jaroslav@291
   137
    The <a href="http://www.w3.org/TR/websockets/">WebSockets</a> specification
jaroslav@291
   138
    usually defines what should happen <em>onopen, onmessage, onclose and onerror</em>.
jaroslav@291
   139
    All these messages are supported in the previous example as well:
jaroslav@291
   140
    <ul>
jaroslav@291
   141
        <li><b>onopen</b> - the <em>queryServer</em> method is called with 
jaroslav@291
   142
            <code>null</code> message
jaroslav@291
   143
        </li>
jaroslav@291
   144
        <li><b>onmessage</b> - the <em>queryServer</em> method is called with 
jaroslav@291
   145
            non-null message
jaroslav@291
   146
        </li>
jaroslav@291
   147
        <li><b>onclose</b> - the <em>anErrorHappened</em> method is called with
jaroslav@291
   148
            <code>null</code> exception
jaroslav@291
   149
        </li>
jaroslav@291
   150
        <li><b>onerror</b> - the <em>anErrorHappened</em> method is called with
jaroslav@291
   151
            non-null exception
jaroslav@291
   152
        </li>
jaroslav@291
   153
    </ul>
jaroslav@291
   154
    Using the <a href="../OnReceive.html">@OnReceive</a> annotation instructs
jaroslav@291
   155
    its associated annotation processor to add appropriate send method
jaroslav@291
   156
    into the generated <code>Comm</code> class. One can use it to establish communication,
jaroslav@291
   157
    send messages and close the communication channel. Here are three methods
jaroslav@291
   158
    showing how to do it:
jaroslav@291
   159
    <pre>
jaroslav@291
   160
    <b>static void </b>connect(Comm c) {
jaroslav@291
   161
      // open a websocket channel:
jaroslav@291
   162
      c.queryServer("ws://server/path", <b>null</b>);
jaroslav@291
   163
      // the method returns immediately and starts establishing the connection
jaroslav@291
   164
      // once that is finished either <b>onopen</b> or <b>onerror</b> type of
jaroslav@291
   165
      // message is delivered
jaroslav@291
   166
    }
jaroslav@291
   167
jaroslav@291
   168
    <b>static void </b>sendMessage(Comm c, Request r) {
jaroslav@291
   169
      // sends the message to already openned websocket channel:
jaroslav@291
   170
      c.queryServer("ws://server/path", r);
jaroslav@291
   171
    }
jaroslav@291
   172
jaroslav@291
   173
    <b>static void </b>disconnect(Comm c) {
jaroslav@291
   174
      // sending <code>null</code> again, closes the connection
jaroslav@291
   175
      c.queryServer("ws://server/path", <b>null</b>);
jaroslav@291
   176
    }
jaroslav@291
   177
    </pre>
jaroslav@291
   178
    One cannot change the URL while a connection is open otherwise one
jaroslav@291
   179
    risks <code>IllegalStateException</code> runtime exceptions. To connect
jaroslav@291
   180
    to different web socket server, one needs to close the connection first and
jaroslav@291
   181
    only later open new one with different URL.
jaroslav@291
   182
    <p>
jaroslav@291
   183
    Enjoy <em>WebSocket</em>s via <a href="../OnReceive.html">@OnReceive</a>!
jaroslav@291
   184
    </body>
jaroslav@291
   185
</html>