Implement real-time messaging with WebSocket
WebSocket is a network protocol that provides a full-duplex communication channel over a single TCP connection. It creates a persistent connection between a client and a server, allowing both to send and receive data at any time. This avoids the overhead and latency of repeatedly establishing new connections, making it more efficient than the traditional HTTP request-response model. WebSocket is primarily used in applications that require real-time communication. ALB supports the WebSocket protocol by default.
Introduction to WebSocket
Why use WebSocket
As web technologies evolve, applications increasingly require servers to push data in real time for features like live chat rooms and real-time comments. The traditional polling method, where a client's browser repeatedly sends HTTP requests to a server to fetch the latest data, has significant drawbacks. Frequent requests with large HTTP headers and small data payloads increase server load and waste bandwidth.
To address these issues, HTML5 introduced the WebSocket protocol, which offers a more efficient solution for client-server communication. WebSocket supports full-duplex communication, meaning the server and client can send and receive data simultaneously. This allows the server to proactively push new data to the client without waiting for a polling request. This bi-directional, real-time communication mechanism improves data transfer efficiency, reduces unnecessary network requests, and saves server resources and bandwidth, providing a smoother and more responsive user experience.
Key features of WebSocket
Communication begins with a standard three-way TCP handshake. The client then sends a special HTTP request, known as a protocol upgrade handshake. Once this handshake is successful, the connection switches from HTTP to WebSocket. All subsequent communication between the client and server uses the WebSocket protocol, allowing for bi-directional data exchange over the same connection.
Once a WebSocket connection is established, it remains active. This persistent, low-latency connection allows for continuous, bi-directional data transfer, which improves data exchange efficiency.
WebSocket communicates using data frames, which have their own frame protocol format with concise headers. Data can be transmitted as text or binary. This method reduces protocol overhead on persistent connections, making network interaction more efficient. It saves server resources and bandwidth while providing a smoother real-time interactive experience.
For more information about the WebSocket protocol, see the official documentation The WebSocket Protocol.
WebSocket use cases
WebSocket is ideal for applications that require fast, real-time, bi-directional communication, such as AI applications, online chat rooms, real-time notification systems, multiplayer online games, and real-time market data feeds.
Example scenario
A company wants to deploy a web-based online chat application on Alibaba Cloud. Users can access the backend service through a domain name for real-time communication. As an instant messaging application, it requires low latency and efficient, real-time, bi-directional communication.
The company's website service faces challenges with high concurrency and persistent connection management. As the number of users grows, the traditional HTTP model cannot support many concurrent users in real-time communication because each interaction requires a new connection. This leads to a sharp increase in server load and poor performance.
In this scenario, using ALB with the WebSocket protocol effectively manages persistent connections under high concurrency. Deploying the application across a server group and using Redis for message synchronization ensures high availability. This provides a reliable and efficient real-time messaging solution for the online chat room application.
Usage notes
HTTP listeners on an ALB instance support the WebSocket protocol by default. ALB supports rolling updates, which means that configuration changes do not interrupt existing persistent connections.
Note the following:
-
If the connection between an ALB instance and a backend server uses a specific HTTP version, such as HTTP/1.1, we recommend that the backend server also support that HTTP version.
-
The default connection request timeout for an HTTP listener is 60 seconds. If no data is exchanged between ALB and a backend server for more than 60 seconds, ALB closes the connection.
-
If the default 60-second timeout is insufficient for your needs, you can modify the listener's Connection Request Timeout.
-
To keep the connection open, you must implement a keepalive mechanism to exchange packets at least once every 60 seconds.
-
Prerequisites
-
An internet-facing ALB instance is required. For more information, see Create and manage an ALB instance.
-
Three ECS instances are required: ECS01, ECS02, and ECS03.
-
ECS01 and ECS02 are used to deploy the WebSocket application, and ECS03 is used to deploy Redis.
-
In this tutorial, all servers run CentOS 7.9.
-
We recommend that you place ECS01, ECS02, and ECS03 in the same security group. If they are in different security groups, make sure to configure rules that allow traffic on the required communication ports between the servers.
-
-
A registered domain name with a completed ICP filing is required. For more information, see Register an Alibaba Cloud domain name and ICP filing.
Procedure
Step 1: Deploy services
You need to deploy Redis on your ECS03 instance and the WebSocket application on your ECS01 and ECS02 instances.
This topic uses a simple Python-based online chat room on CentOS 7.9 for demonstration purposes. This example is for reference only. In a production environment, use your own application.
Deploy Redis on ECS03
-
Log on to the ECS03 instance.
-
Copy and run the following commands to install and configure Redis.
# Install EPEL (Extra Packages for Enterprise Linux) sudo yum install epel-release -y # Install Redis sudo yum install redis -y # Start and enable the Redis service sudo systemctl start redis sudo systemctl enable redis # Edit the Redis configuration file to allow remote connections sudo sed -i 's/^bind 127.0.0.1$/bind 0.0.0.0/' /etc/redis.conf sudo sed -i 's/^protected-mode yes/protected-mode no/' /etc/redis.conf # Restart the Redis service for the changes to take effect sudo systemctl restart redis # Check the Redis status sudo systemctl status redis -
If the commands run without errors and the output shows the Redis service is in the active (running) state, the deployment and configuration are successful.
● redis.service - Redis persistent key-value database Loaded: loaded (/usr/lib/systemd/system/redis.service; enabled; vendor preset: disabled) Active: active (running) since ... Main PID: 12345 (redis-server) CGroup: /system.slice/redis.service └─12345 /usr/bin/redis-server 0.0.0.0:6379
Deploy WebSocket on ECS01
-
Log on to the ECS01 instance.
-
Run
sudo pip3 install flask flask-socketio flask-cors redisto install the dependencies. -
Run
vi ECS01_ws.pyand press theikey to enter edit mode. -
Copy and paste the following code:
-
Press the
Esckey, and then enter:wqto save the changes. -
Run the
sudo python3 ECS01_ws.pycommand to run the script. -
When the following output is displayed, the WebSocket application has started on port 5000.
Server initialized for threading. * Serving Flask app 'ECS01_ws' (lazy loading) * Environment: production WARNING: This is a development server. Do not use it in a production deployment. Use a production WSGI server instead. * Debug mode: off * Running on all addresses. WARNING: This is a development server. Do not use it in a production deployment. * Running on http://192.168.*.*:5000/ (Press CTRL+C to quit)If the application fails to start, check if the port is already in use or if you copied the commands or code incorrectly.
● redis.service – Redis persistent key-value database
Loaded: loaded (/usr/lib/systemd/system/redis.service; enabled; vendor preset: disabled)
Drop-In: /etc/systemd/redis.service.d
└─limit.conf
Active: active (running) since Thu 2xxx xxx xxx xxx CST; 6s ago
Process: 14715 ExecStop=/usr/libexec/redis-shutdown (code=exited, status=0/SUCCESS)
Main PID: 14730 (redis-server)
CGroup: /system.slice/redis.service
└─14730 /usr/bin/redis-server 0.0.0.0:6379
Deploy WebSocket on ECS02
-
Log on to the ECS02 instance.
-
Run
sudo pip3 install flask flask-socketio flask-cors redisto install the dependencies. -
Run
vi ECS02_ws.pyand press theikey to enter edit mode. -
Copy and paste the following code:
-
Press the
Esckey, and then enter:wqto save the changes. -
Run the
sudo python3 ECS02_ws.pycommand to run the script. -
When the following output is displayed, the WebSocket application has started on port 5000.
Server initialized for threading. * Serving Flask app 'ECS02_ws' (lazy loading) * Environment: production WARNING: This is a development server. Do not use it in a production deployment. Use a production WSGI server instead. * Debug mode: off * Running on all addresses. WARNING: This is a development server. Do not use it in a production deployment. * Running on http://192.168.*.*:5000/ (Press CTRL+C to quit)If the application fails to start, check if the port is already in use or if you copied the commands or code incorrectly.
Step 2: Configure a server group
-
Log on to the ALB console.
-
In the top navigation bar, select the region where the instance is deployed.
-
In the left-side navigation pane, click Server Group.
-
Click Create Server Group. On the Create Server Group page, configure the following parameters, leave the others at their default values, and click Create.
Parameter
Description
Server Group Type
Select Server.
VPC
Select the VPC where the backend servers ECS01 and ECS02 are located.
The backend servers must be in the same VPC as the ALB instance.
-
In the The server group is created dialog box, click Add Backend Server.
-
On the Add Backend Server page, select ECS01 and ECS02 and add them to the server group. Set their port to 5000, which is the port used by the WebSocket application in this tutorial.
Step 3: Configure an HTTP listener
-
Log on to the ALB console.
-
In the top navigation bar, select the region where the instance is deployed.
-
In the left-side navigation pane, select Instances.
-
On the Instances page, find the target instance, and then click Create Listener in the Actions column.
-
On the Configure Listener page, configure the following parameters and leave the other parameters with their default values. Then, click Next.
Parameter
Description
Select Listener Protocol
Select HTTP.
Listener Port
Set the port to 5000.
-
On the Server Group page, configure the following parameter and leave the other parameters with their default values. Then, click Next.
Parameter
Description
Server Group
Select the server group that you created.
-
On the Confirm page, review the settings and click Submit. Then, wait for the listener to be created.
Step 4: Configure DNS resolution
For production, we recommend mapping a custom domain name to the ALB instance's domain name by creating a CNAME record.
-
In the left-side navigation pane, choose .
-
On the Instances page, copy the DNS name of the created ALB instance.
-
Follow these steps to add a CNAME record.
NoteIf your domain name is registered by a provider other than Alibaba Cloud, you must add the domain name to the Alibaba Cloud DNS console before you can configure DNS resolution. For more information, see Manage domain names. If your domain name is registered with Alibaba Cloud, proceed with the following steps.
-
Log on to the Alibaba Cloud DNS console.
-
On the Authoritative DNS Resolution page, find the target domain name, and click Settings in the Operations column.
-
On the Settings page, click Add Record.
-
In the Add Record panel, configure the CNAME record by setting the following parameters, and then click OK.
Parameter
Description
Record Type
Select CNAME from the drop-down list.
Hostname
The prefix of your domain name. This tutorial uses @.
NoteTo use a root domain, set the hostname to
@.Query Source
Select Default.
Record Value
Enter the DNS name of the ALB instance that you copied.
TTL
Time to live (TTL) is the duration that a DNS record is cached on a DNS server. Use the default value.
-
Step 5: Verify the result
Verify that ALB delivers real-time messages over WebSocket by opening the application in a browser on two separate computers and exchanging messages.
-
In a browser, go to
http://<your-domain-name>:5000to access the online chat room application.The Online Chat Room interface loads. The message "You have entered the chat room!" appears in the chat message area, which indicates that the WebSocket connection is established. The page contains a username setting area with a Set Username button and a message sending area with a Send button.
If you open your browser's developer tools, the Network tab shows that the browser is communicating using the WebSocket protocol.
In the Network panel, set the filter to
websocket. A WebSocket request with a status code of 101 indicates that the protocol upgrade was successful. The connection status is Pending, which means that the persistent WebSocket connection is established and active. -
Enter a username for the chat and click Set Username.
-
On each computer, enter multiple chat messages and click Send to test the application.
Both browsers receive the messages in real time.
The Online Chat Room application is successfully deployed. The page contains a Username input box and a Set Username button, a chat message display area, and a message input box with a Send button at the bottom. Multiple users, such as User1 and User2, can have a real-time conversation in the chat room.
-
This confirms that ALB provides real-time, high-availability messaging over WebSocket.
FAQ
How do I use WebSocket Secure?
WebSocket Secure is the encrypted version of the WebSocket protocol.
HTTPS listeners support WebSocket Secure by default. To use WebSocket Secure, select HTTPS when you configure the listener.
Am I charged for using WebSocket?
WebSocket and WebSocket Secure do not incur additional charges.
Which regions support WebSocket?
All regions that support ALB also support WebSocket and WebSocket Secure.
References
This tutorial demonstrates deploying Redis on an ECS instance for testing. However, a single Redis server is a potential single point of failure. For production environments, we recommend that you use Tair to ensure high availability. For more information, see Quick start for Tair.