Search Results for

    Show / Hide Table of Contents

    WebSockets

    Overview

    WebSocket support in Sparkle enables real-time, bidirectional communication between clients and servers. WebSockets are essential for applications that require instant data updates, such as chat applications, live notifications, and real-time data feeds. This chapter covers how to enable and use WebSockets in your server applications, focusing on the key operations such as upgrading HTTP requests to WebSocket connections, sending and receiving data, and managing WebSocket states.

    If you're unfamiliar with WebSockets, you can learn more about the protocol on the WebSocket Wikipedia page.

    Note

    WebSockets are only available for Delphi XE8 or newer.

    Key Operations

    Upgrading an HTTP Request to WebSocket

    To handle WebSocket connections, you first need to upgrade the incoming HTTP request to a WebSocket connection. This is done using the Upgrade method from the IWebSocketUpgrader interface. The upgrader checks if the incoming request is a WebSocket request and, if so, upgrades it to a WebSocket connection.

    Example:

    var
      Upgrader: IWebSocketUpgrader;
      WebSocket: IWebSocket;
    begin
      Upgrader := THttpServerContext.Current.Item<IWebSocketUpgrader>;
      if Upgrader <> nil then
        WebSocket := Upgrader.Upgrade;
    end;
    
    • Upgrader: The IWebSocketUpgrader instance retrieved from the current HTTP context.
    • Upgrade: If the request is a WebSocket request, the Upgrade method upgrades the connection and returns an instance of IWebSocket for managing the connection.

    Sending and Receiving Data

    Once the connection is upgraded, you can start sending and receiving WebSocket messages using the Send, Receive, SendFrame, and ReceiveFrame methods from the IWebSocket interface. Sparkle provides two primary methods for handling WebSocket communication:

    1. Send / Receive: These methods handle full WebSocket messages, automatically managing fragmented messages.

    Sending a Message:

    WebSocket.Send('Hello, WebSocket!');
    

    Receiving a Message:

    var
      Msg: IWebSocketMessage;
    begin
      Msg := WebSocket.Receive;
      if Msg.MessageType = TWebSocketMessageType.Text then
        Log('Received: ' + Msg.Text);
    end;
    
    1. SendFrame / ReceiveFrame: These methods allow for lower-level control by sending and receiving individual WebSocket frames. This is useful when you need to manage fragmented messages manually.

    Sending a Frame:

    WebSocket.SendFrame(Buffer, Count, TWebSocketMessageType.Text, EndOfMessage);
    

    Receiving a Frame:

    var
      Result: TWebSocketReceiveResult;
    begin
      Result := WebSocket.ReceiveFrame(Buffer, Count);
      if Result.EndOfMessage then
        Log('Message received.');
    end;
    
    Warning

    If you use SendFrame / ReceiveFrame, you must ensure that a full message is sent or received before switching to Send / Receive methods. Mixing these methods improperly can cause errors, as Send / Receive expects a complete message.

    Managing WebSocket State

    The State property from the IWebSocket interface provides access to the current state of the WebSocket connection, represented by the TWebSocketState enumeration.

    • State: The State property returns the current state of the WebSocket connection.

        if WebSocket.State = TWebSocketState.Open then
          Log('Connection is open.');
      
    • Close / SendClose: To close the WebSocket connection, use the Close method to initiate the closing handshake, or SendClose to respond to a received close frame.

        WebSocket.Close(WebSocketStatusCodes.NormalClosure);
      

    Example: Implementing a WebSocket Service

    Here is an example of how to implement a WebSocket service that echoes messages back to the client:

    [ServiceImplementation]
    TWebSocketService = class(TInterfacedObject, IWebSocketService)
    private
      procedure Echo;
    end;
    
    procedure TWebSocketService.Echo;
    var
      Upgrader: IWebSocketUpgrader;
      WebSocket: IWebSocket;
      Msg: IWebSocketMessage;
    begin
      // Check if the request is a WebSocket request and upgrade it
      Upgrader := THttpServerContext.Current.Item<IWebSocketUpgrader>;
      if Upgrader = nil then
      begin
        TXDataOperationContext.Current.Handler.SetStatusCode(400);
        Exit;
      end;
    
      // Upgrade the connection to WebSocket
      WebSocket := Upgrader.Upgrade;
    
      // Echo received messages back to the client
      while WebSocket.State = TWebSocketState.Open do
      begin
        Msg := WebSocket.Receive;
        case Msg.MessageType of
          TWebSocketMessageType.Text:
            WebSocket.Send('Echo: ' + Msg.Text);
          TWebSocketMessageType.Close:
            WebSocket.SendClose(WebSocketStatusCodes.NormalClosure);
        end;
      end;
    end;
    
    initialization
      RegisterServiceType(TWebSocketService);
    

    Explanation:

    • Upgrade Request: The Echo method checks if the incoming request is a WebSocket request and upgrades it if necessary.
    • Send / Receive: Once the connection is upgraded, the server enters a loop, receiving messages and echoing them back to the client.
    • SendClose: When a close frame is received from the client, the server responds with SendClose to complete the handshake and close the connection gracefully.

    For further reading, you can check out more details about WebSockets on Wikipedia.

    In This Article
    Back to top TMS Sparkle v3.32
    © 2002 - 2025 tmssoftware.com