Introduction
A Server-Side Component consists of a state object, a set of actions, and arender function.
The typical lifecycle:
- The component is rendered as part of a view
- Elements inside the component can call server-side actions using a simple JavaScript library
- On the server-side, actions are evaluated and a new state object is generated
- The new state triggers a re-render
- The re-rendered content is diffed with existing HTML and update instructions are sent to the client
- Repeat at step 2
- The component is stopped when the page is closed
The Server-Side Component toolkit has been tested in production environments. While the API is mostly stable, some changes may occur in future versions.
Creating a Component
In this example we’re building a counter component: The counter shows a number. When a button is clicked, the number will be incremented.Add to FrontController
Open Add Now the websocket server for Counter is activated.
Web/FrontController.hs and add imports:routeComponent @Counter:Use the component
Open Change the welcome view:
Web/View/Static/Welcome.hs and add imports:If this doesn’t compile, make sure
TypeApplications is enabled for the module (add {-# LANGUAGE TypeApplications #-} at the top).WelcomeView you will see the newly created counter.
Advanced
Actions with Parameters
Actions can accept parameters:Fetching from the Database
You can use typical IHP database operations likequery @Post or createRecord from your actions.
To fill initial data, use the componentDidMount lifecycle function:
componentDidMount gets passed the initial state and returns a new state. It’s called right after the first render once the client has wired up the WebSocket connection.
HTML Diffing & Patching
IHP uses a HTML Diff & Patch approach to update the component’s HTML. When thePlus One button is clicked, the client sends:
Current: 0 to Current: 1.
This is useful if you have many interactive elements controlled by JavaScript libraries (e.g., a <video> element). As long as their HTML doesn’t change on the server-side, the DOM nodes won’t be touched.
Example Components
See more examples:Error Handling
Server-Side Components include built-in error handling for common failure scenarios.Action Errors
When an action handler throws an exception, the error is:- Logged on the server with full details
- Sent to the client with a generic error message
- Displayed to the user temporarily (auto-dismisses after 5 seconds)
Custom Error Handling
You can listen for SSC errors in JavaScript:Parse Errors
If the client sends an invalid action payload (e.g., malformed JSON or unknown action), the server logs the error and sends anSSCParseError to the client.
Connection Resilience
The SSC JavaScript client automatically handles connection issues.Automatic Reconnection
When the WebSocket connection is lost, the client will:- Automatically attempt to reconnect with exponential backoff
- Show a visual indicator of the connection state
- Queue any actions triggered while disconnected
- Replay queued actions once reconnected
Connection States
The client tracks these states:- Connecting: Initial connection in progress
- Connected: WebSocket is open and ready
- Reconnecting: Attempting to restore a lost connection
- Failed: Max reconnection attempts reached
Visibility Change Handling
When a browser tab becomes visible again, the client will attempt to reconnect if the connection was lost while the tab was in the background.Manual Retry
If automatic reconnection fails, a “Retry” button is shown to allow manual reconnection.Production Considerations
WebSocket Scaling
Each SSC component maintains an active WebSocket connection. Consider:- Connection Limits: Monitor concurrent WebSocket connections per server process
- Sticky Sessions: Enable session affinity on your load balancer for WebSocket routing
- Timeouts: Configure appropriate WebSocket timeout settings
State Management
Component state is held in memory on the server:- State Size: Keep component state small to minimize memory usage
- Ephemeral State: Component state is lost when the connection closes or server restarts
- State Recovery: After reconnection, the component reinitializes with
initialStateandcomponentDidMount
Monitoring
IHP SSC logs lifecycle events:- Component connections and disconnections
- Action execution errors
- Parse errors from invalid client messages
Security Considerations
- Action Validation: Validate all action parameters
- Authorization: Check user permissions in action handlers for sensitive data
- Rate Limiting: Consider rate limiting for expensive operations