# `http_websocket`

This library provides high-level WebSocket predicates for opening and closing connections, for exchanging messages, and for running common client and server session loops.

By default, client predicates select a transport from the WebSocket URL scheme: `ws://` uses `http_socket_transport` and `wss://` uses `http_process_transport`. Server predicates that accept an already open listener default to `http_socket_transport`. Applications can select a transport explicitly with the `transport/1` option when they need lower-level control or a custom `http_transport_protocol` implementation.

This library can be used with backend Prolog systems that support unbound integer arithmetic and the `sockets` library: ECLiPSe, SICStus Prolog, SWI-Prolog, Trealla Prolog, and XVM.

## API documentation

Open the ../../apis/library_index.html#http_websocket link in a web browser.

## Loading

To load the full library, load the `loader.lgt` file:

    | ?- logtalk_load(http_websocket(loader)).

## Testing

To test this library, load the `tester.lgt` file:

    | ?- logtalk_load(http_websocket(tester)).

## Current scope

The current implementation provides the following predicates:

- `open/2-3` for opening client WebSocket connections and returning opaque handles. The `transport/1` option selects the transport; `transport(default)` derives it from the URL scheme.

- `accept/3-4` for accepting one server-side WebSocket connection on an open listener and returning opaque handles. The listener must be created by the selected transport. Use `transport(Transport)` when accepting from a listener opened with a transport other than `http_socket_transport`.

- `send/2-3`, `receive/2-3`, and `close/1-2` for direct message exchange using those handles.

- `property/2` for inspecting handle properties such as the handshake response, selected subprotocol, or underlying upgraded connection.

- `send_text/2`, `receive_text/2`, `send_binary/2`, `receive_binary/2`, `send_json/2`, `receive_json/2`, `send_term/2`, and `receive_term/2` convenience predicates for common payload formats.

- `open_session/4-5` and `serve_once/5-6` for callback-driven client and server sessions built on top of the `http_websocket_service` layer.

The test suite exercises both `http_socket_transport` and `http_process_transport` by passing the selected transport through the `transport/1` option.

## Current workflow

For the common direct client case:

| ?- http_websocket::open(‘ws://127.0.0.1:8080/echo’, WebSocket, [protocols([chat])]), http_websocket::send_text(WebSocket, hello), http_websocket::receive_text(WebSocket, Reply), http_websocket::close(WebSocket, status(1000, done)).

For the common direct server case:

| ?- http_socket_transport::open_listener(‘127.0.0.1’, 8080, Listener, []), http_websocket::accept(Listener, WebSocket, ClientInfo, [transport(http_socket_transport), protocol(chat)]), http_websocket::receive(WebSocket, Message), http_websocket::send(WebSocket, Message).

To use the process-backed transport instead, pair the matching listener and `transport/1` option:

| ?- http_process_transport::open_listener(‘127.0.0.1’, 8080, Listener, []), http_websocket::accept(Listener, WebSocket, ClientInfo, [transport(http_process_transport), protocol(chat)]), http_websocket::receive(WebSocket, Message), http_websocket::send(WebSocket, Message).

For callback-driven client sessions that should stay on the high-level surface, use:

| ?- http_websocket::open_session(URL, Handler, Response, State, [transport(default), protocols([chat]), initial_messages([message(text, hello)])]).

For callback-driven server sessions that should stay on the high-level surface, use:

| ?- http_websocket::serve_once(Listener, Handler, Response, State, ClientInfo, [transport(http_socket_transport), protocol(chat)]).

## Lower-level layers

The `http_websocket` library now hides the most common plumbing, but the lower-level libraries remain available when you need them:

- Use `http_websocket_frames` when working with raw frame parsing and generation.

- Use `http_websocket_messages` when you want transport-neutral message I/O without connection or session ownership.

- Use `http_websocket_session` when you need the stateful message layer with detailed close/ping state control but without callback loops or threads.

- Use `http_websocket_service` when you need the full callback-driven session layer or registry-backed broadcast helpers.