View Source Antikythera.Websocket behaviour (antikythera v0.5.1)

Behaviour module for websocket handlers.

Note the naming convention of the websocket-related modules; we use Websocket, WebSocket is not allowed.

Websocket module of gears must use this module as in the example below. use Antikythera.Websocket implicitly invokes use Antikythera.Controller, for convenience in implementing connect/1 callback.

Example

The following example simply echoes back messages from client:

defmodule MyGear.Websocket do
  use Antikythera.Websocket

  def init(_conn) do
    {%{}, []}
  end

  def handle_client_message(state, _conn, frame) do
    {state, [frame]}
  end

  def handle_server_message(state, _conn, _msg) do
    {state, []}
  end
end

Name registration

Once a websocket connection is established, subsequent bidirectional communication is handled by a dedicated connection process. To send websocket frames to the connected client, you should first be able to send messages to the connection process when a particular event occurs somewhere in the cluster. To this end antikythera provides a process registry mechanism which makes connection processes accessible by "name"s.

To register connection processes, call Antikythera.Registry.Unique.register/2 and/or Antikythera.Registry.Group.join/2 in your init/1 implementation. Then, to notify events of connection processes, use Antikythera.Registry.Unique.send_message/3 or Antikythera.Registry.Group.publish/3. Finally to send websocket message from a connection process to client, implement handle_server_message/3 callback so that it returns an appropriate websocket frame using the message.

See Antikythera.Registry.Unique and Antikythera.Registry.Group for more detail of the registry.

Summary

Types

Type of return value of init/1, handle_client_message/3 and handle_server_message/3 callbacks. The 1st element of the return value is used as the new state. The 2nd element of the return value is sent to the client.

Callbacks

Callback function to be used during websocket handshake request.

Callback function to be called on receipt of a client message.

Callback function to be called on receipt of a message from other process in the cluster.

Callback function to be called right after a connection is established.

Callback function to clean up resources used by the websocket connection.

Types

@type callback_result() :: {state(), Antikythera.Websocket.FrameList.t()}

Type of return value of init/1, handle_client_message/3 and handle_server_message/3 callbacks. The 1st element of the return value is used as the new state. The 2nd element of the return value is sent to the client.

To close the connection, include a :close frame in the 2nd element of the return value. Note that the remaining frames after the close frame will not be sent.

@type state() :: any()
@type terminate_reason() ::
  :normal
  | :stop
  | :timeout
  | :remote
  | {:remote, Antikythera.Websocket.Frame.close_code(),
     Antikythera.Websocket.Frame.close_payload()}
  | {:error, any()}

Callbacks

@callback connect(Antikythera.Conn.t()) :: Antikythera.Conn.t()

Callback function to be used during websocket handshake request.

This callback is implemented in basically the same way as ordinary controller actions. You can use plugs and controller helper functions. The only difference is that on success this function returns a Antikythera.Conn.t without setting an HTTP status code.

This callback is responsible for authenticating/authorizing the client. If the client is valid and it's OK to start websocket communication, implementation of this callback must return the given Antikythera.Conn.t. On the other hand if the client is not allowed to open websocket connection, this function must return an error as a usual HTTP response.

use Antikythera.Websocket generates a default implementation of this callback, which just returns the given Antikythera.Conn.t. Note that you can use plugs without overriding the default.

Link to this callback

handle_client_message(state, t, t)

View Source
@callback handle_client_message(
  state(),
  Antikythera.Conn.t(),
  Antikythera.Websocket.Frame.t()
) ::
  callback_result()

Callback function to be called on receipt of a client message.

Link to this callback

handle_server_message(state, t, any)

View Source
@callback handle_server_message(state(), Antikythera.Conn.t(), any()) :: callback_result()

Callback function to be called on receipt of a message from other process in the cluster.

@callback init(Antikythera.Conn.t()) :: callback_result()

Callback function to be called right after a connection is established.

This callback is responsible for:

  1. initialize the process state (1st element of return value)
  2. send initial message to client (2nd element of return value)
  3. register the process to make it accessible from other processes in the system (see "Name registration" above)
Link to this callback

terminate(state, t, terminate_reason)

View Source
@callback terminate(state(), Antikythera.Conn.t(), terminate_reason()) :: any()

Callback function to clean up resources used by the websocket connection.

For typical use cases you don't need to implement this callback; Antikythera.Websocket generates a default implementation (which does nothing) for you.