STTNet 0.7.0

第 10 章:客户端

本章介绍 HTTP、WebSocket、TCP 和 UDP 客户端的调用模型,以及它们与服务端 Reactor 的线程边界。

1. 客户端是同步还是异步

客户端模型
TcpClient默认阻塞;连接、发送、接收都应设置合理超时。
HttpClient同步请求;发送成功仅表示请求已写出,isReturn() 表示是否获得有效响应。
WebSocketClient连接和发送接口配合内部监听线程,消息回调异步执行。
UdpClient直接发送/接收 datagram,可选择阻塞或非阻塞。
阻塞式 HttpClient/TcpClient 请求会暂停 Server 的 Reactor。外部服务调用适合放入 WorkerPool,并配置有限超时。

2. HTTP Client Demo

#include <sttnet.h>

#include <iostream>

int main()
{
    using stt::network::HttpClient;

    // HttpClient 是同步客户端;生产环境为连接和读取设置有限超时,
    // 调用发生在 WorkerPool 等非 Reactor 上下文中。
    HttpClient client;

    if(!client.getRequest("http://127.0.0.1:8080/ping", "",
                          "Connection: close", 5))
    {
        std::cerr << "request could not be sent\n";
        return 1;
    }

    // 发送成功不等于已经收到完整响应。
    if(!client.isReturn())
    {
        std::cerr << "server did not return a complete HTTP response\n";
        return 2;
    }

    std::cout << "--- response headers ---\n" << client.header
              << "\n--- response body ---\n" << client.body << '\n';
    return 0;
}

HTTP Client Demo 需要一个正在运行的 sttnet_http_hello 服务端:

./build/examples/sttnet_http_hello
# 另一终端
./build/examples/sttnet_http_client

3. WebSocket Client Demo

#include <sttnet.h>

#include <chrono>
#include <iostream>
#include <thread>

int main()
{
    using stt::network::WebSocketClient;

    WebSocketClient client;

    // 回调运行在客户端内部监听线程。
    client.setFunction(
        [](const std::string &message, WebSocketClient &) {
            std::cout << "received: " << message << '\n';
            return true; // 返回 false 会关闭 WebSocket 连接。
        });

    if(!client.connect("ws://127.0.0.1:5050/echo"))
    {
        std::cerr << "WebSocket connection failed\n";
        return 1;
    }

    if(!client.sendMessage("hello from STTNet client"))
    {
        std::cerr << "send failed\n";
        client.close(1011, "send failed");
        return 2;
    }

    // 给异步接收回调留出打印回显的时间。
    std::this_thread::sleep_for(std::chrono::seconds(1));
    client.close(1000, "demo complete");
    return 0;
}

WebSocket Client Demo 需要一个正在运行的 WebSocket 服务端:

./build/examples/sttnet_websocket_echo
# 另一终端
./build/examples/sttnet_websocket_client

4. URL 组成

客户端 URL 要显式包含协议、端口和路径,例如 https://example.com:443/ws://127.0.0.1:5050/echo。TLS 客户端会进行证书链和主机名校验。