1. Boost.Asio 网络编程基础
Boost.Asio 是 C++ 网络编程的核心库,它提供了跨平台的异步 I/O 功能。让我们深入探讨其核心组件和工作原理。
1.1 io_context:事件循环引擎
io_context 是 Boost.Asio 的核心,负责调度和执行所有异步操作。它的工作方式类似于 Node.js 的事件循环或 Linux 的 epoll 机制。
cpp复制#include <boost/asio.hpp>
int main() {
// 创建事件循环对象
boost::asio::io_context ioc;
// 在这里注册各种异步操作...
// 启动事件循环(阻塞直到所有任务完成)
ioc.run();
return 0;
}
关键特性解析:
- run():阻塞调用,处理所有已注册的异步事件
- 单线程模型:默认情况下,run() 在单线程中顺序处理事件
- 多线程扩展:可以在多个线程中调用 run() 实现并发处理
实际经验:在服务器开发中,通常会创建多个 io_context 实例组成线程池,每个线程运行一个 io_context 的 run() 方法,这样可以充分利用多核 CPU。
1.2 异步操作模型详解
Boost.Asio 采用 Proactor 模式实现异步 I/O,与传统的 Reactor 模式相比有显著优势:
-
操作流程:
- 发起异步操作(如 async_read)
- 操作系统在后台执行实际 I/O
- 操作完成后,回调函数被调用
-
代码示例:
cpp复制// 异步读取示例
socket.async_read_some(
boost::asio::buffer(data, max_length),
[this](const boost::system::error_code& ec, std::size_t bytes_transferred) {
if (!ec) {
// 处理接收到的数据
ProcessData(data, bytes_transferred);
} else {
HandleError(ec);
}
}
);
- 与同步操作对比:
特性 同步 I/O 异步 I/O 阻塞 是 否 性能 低 高 复杂度 简单 较高 适用场景 简单客户端 高性能服务器
1.3 TCP 编程实战
服务器端实现
构建 TCP 服务器需要以下几个关键组件:
- acceptor:监听连接请求
- socket:处理客户端连接
- 异步回调链:处理连接生命周期
完整服务器示例:
cpp复制class TcpServer {
public:
TcpServer(boost::asio::io_context& ioc, short port)
: acceptor_(ioc, tcp::endpoint(tcp::v4(), port)) {
StartAccept();
}
private:
void StartAccept() {
// 创建新socket
auto socket = std::make_shared<tcp::socket>(acceptor_.get_executor());
// 异步接受连接
acceptor_.async_accept(*socket,
[this, socket](const boost::system::error_code& ec) {
if (!ec) {
// 连接成功,处理新客户端
HandleConnection(socket);
}
// 继续接受新连接
StartAccept();
});
}
void HandleConnection(std::shared_ptr<tcp::socket> socket) {
// 这里实现具体的连接处理逻辑
AsyncRead(socket);
}
tcp::acceptor acceptor_;
};
客户端实现
客户端连接服务器的基本流程:
cpp复制boost::asio::io_context io_context;
tcp::socket socket(io_context);
// 同步连接方式
try {
socket.connect(server_endpoint);
std::cout << "Connected successfully" << std::endl;
} catch (const boost::system::system_error& e) {
std::cerr << "Connection failed: " << e.what() << std::endl;
}
// 异步连接方式
socket.async_connect(server_endpoint,
[](const boost::system::error_code& ec) {
if (!ec) {
std::cout << "Connected successfully" << std::endl;
} else {
std::cerr << "Connection failed: " << ec.message() << std::endl;
}
});
1.4 信号处理机制
服务器需要优雅地处理系统信号,如 SIGINT (Ctrl+C) 和 SIGTERM:
cpp复制boost::asio::io_context ioc;
boost::asio::signal_set signals(ioc, SIGINT, SIGTERM);
signals.async_wait([&ioc](const boost::system::error_code&, int signal_number) {
std::cout << "Received signal " << signal_number
<< ", shutting down..." << std::endl;
ioc.stop(); // 停止事件循环
});
// 在其他线程运行事件循环
std::thread io_thread([&ioc]() { ioc.run(); });
// ...服务器其他逻辑...
io_thread.join(); // 等待事件循环结束
注意事项:信号处理应该在主线程中设置,但 io_context 可以在其他线程运行。确保在收到信号后有序关闭所有资源。
2. 高性能服务器架构设计
2.1 IO 线程池实现
单线程 io_context 无法充分利用多核 CPU,我们需要实现 IO 线程池:
cpp复制class IoThreadPool {
public:
explicit IoThreadPool(size_t pool_size = std::thread::hardware_concurrency())
: next_io_context_(0) {
// 创建多个io_context和对应的work
for (size_t i = 0; i < pool_size; ++i) {
io_contexts_.emplace_back(std::make_unique<boost::asio::io_context>());
works_.emplace_back(boost::asio::make_work_guard(*io_contexts_.back()));
}
// 为每个io_context创建线程
for (auto& ioc : io_contexts_) {
threads_.emplace_back([&ioc]() { ioc->run(); });
}
}
boost::asio::io_context& GetIoContext() {
// 简单轮询分配
auto& ioc = *io_contexts_[next_io_context_++];
if (next_io_context_ == io_contexts_.size()) {
next_io_context_ = 0;
}
return ioc;
}
void Stop() {
// 清除work,允许io_context自然结束
for (auto& work : works_) {
work.reset();
}
// 停止所有io_context
for (auto& ioc : io_contexts_) {
ioc->stop();
}
// 等待所有线程结束
for (auto& t : threads_) {
if (t.joinable()) t.join();
}
}
private:
std::vector<std::unique_ptr<boost::asio::io_context>> io_contexts_;
std::vector<boost::asio::executor_work_guard<
boost::asio::io_context::executor_type>> works_;
std::vector<std::thread> threads_;
std::atomic_size_t next_io_context_;
};
关键设计点:
- work_guard:防止 io_context 在没有任务时立即退出
- 负载均衡:使用轮询算法分配连接
- 优雅关闭:先移除 work,再停止 io_context,最后 join 线程
2.2 会话管理设计
每个客户端连接需要一个独立的会话对象管理其状态:
cpp复制class Session : public std::enable_shared_from_this<Session> {
public:
Session(boost::asio::ip::tcp::socket socket)
: socket_(std::move(socket)) {}
void Start() {
DoRead();
}
private:
void DoRead() {
auto self(shared_from_this());
socket_.async_read_some(boost::asio::buffer(data_),
[this, self](boost::system::error_code ec, std::size_t length) {
if (!ec) {
ProcessData(length);
DoRead(); // 继续读取
} else {
// 处理断开连接
}
});
}
void DoWrite(std::size_t length) {
auto self(shared_from_this());
boost::asio::async_write(socket_, boost::asio::buffer(data_, length),
[this, self](boost::system::error_code ec, std::size_t /*length*/) {
if (!ec) {
DoRead(); // 写完后继续读取
}
});
}
boost::asio::ip::tcp::socket socket_;
std::array<char, 1024> data_;
};
2.3 消息协议设计
即时通讯服务器需要定义应用层协议,常见的设计:
-
消息头格式:
- 消息ID:2字节
- 消息长度:2字节
- 版本号:1字节
- 保留字段:1字节
-
消息体格式:
- 变长内容,由消息长度字段指定
-
字节序处理:
cpp复制// 主机序转网络序
uint16_t host_to_network(uint16_t value) {
return boost::asio::detail::socket_ops::host_to_network_short(value);
}
// 网络序转主机序
uint16_t network_to_host(uint16_t value) {
return boost::asio::detail::socket_ops::network_to_host_short(value);
}
- 消息解析示例:
cpp复制void ParseMessage(const char* data, size_t length) {
if (length < HEADER_SIZE) return;
// 读取消息头
uint16_t msg_id = network_to_host(*reinterpret_cast<const uint16_t*>(data));
uint16_t msg_len = network_to_host(*reinterpret_cast<const uint16_t*>(data + 2));
// 验证消息长度
if (length < HEADER_SIZE + msg_len) return;
// 处理消息体
const char* body = data + HEADER_SIZE;
ProcessMessage(msg_id, body, msg_len);
}
2.4 性能优化技巧
-
缓冲区管理:
- 使用预分配的固定大小缓冲区
- 考虑使用内存池减少内存碎片
-
零拷贝技术:
- 使用 boost::asio::buffer 直接引用现有内存
- 避免不必要的数据拷贝
-
批量操作:
- 合并小消息为批量传输
- 使用 gather-write 发送多个缓冲区
-
连接池:
- 对数据库等后端服务使用连接池
- 复用 TCP 连接减少握手开销
-
日志优化:
- 异步日志系统避免阻塞 I/O 线程
- 使用轻量级日志库如 spdlog
3. HTTP/WebSocket 支持
3.1 使用 Boost.Beast 处理 HTTP
Boost.Beast 是基于 Boost.Asio 的 HTTP/WebSocket 库:
cpp复制#include <boost/beast.hpp>
#include <boost/beast/http.hpp>
namespace beast = boost::beast;
namespace http = beast::http;
class HttpSession : public std::enable_shared_from_this<HttpSession> {
public:
HttpSession(boost::asio::ip::tcp::socket socket)
: socket_(std::move(socket)) {}
void Start() {
ReadRequest();
}
private:
void ReadRequest() {
auto self = shared_from_this();
http::async_read(socket_, buffer_, request_,
[self](beast::error_code ec, std::size_t bytes_transferred) {
if (!ec) {
self->ProcessRequest();
}
});
}
void ProcessRequest() {
response_.version(request_.version());
response_.keep_alive(false);
switch (request_.method()) {
case http::verb::get:
response_.result(http::status::ok);
response_.set(http::field::content_type, "text/html");
beast::ostream(response_.body()) << "<html><body>Hello World</body></html>";
break;
default:
response_.result(http::status::bad_request);
beast::ostream(response_.body()) << "Invalid request method";
break;
}
WriteResponse();
}
void WriteResponse() {
auto self = shared_from_this();
response_.content_length(response_.body().size());
http::async_write(socket_, response_,
[self](beast::error_code ec, std::size_t) {
self->socket_.shutdown(boost::asio::ip::tcp::socket::shutdown_send, ec);
});
}
boost::asio::ip::tcp::socket socket_;
beast::flat_buffer buffer_{8192};
http::request<http::dynamic_body> request_;
http::response<http::dynamic_body> response_;
};
3.2 WebSocket 实现
WebSocket 是现代即时通讯的常用协议:
cpp复制class WebSocketSession : public std::enable_shared_from_this<WebSocketSession> {
public:
explicit WebSocketSession(boost::asio::ip::tcp::socket socket)
: ws_(std::move(socket)) {}
void Run() {
ws_.async_accept(
[self = shared_from_this()](beast::error_code ec) {
if (!ec) {
self->DoRead();
}
});
}
private:
void DoRead() {
ws_.async_read(buffer_,
[self = shared_from_this()](beast::error_code ec, std::size_t bytes_transferred) {
if (!ec) {
// 处理收到的消息
std::string message = beast::buffers_to_string(self->buffer_.data());
self->ProcessMessage(message);
// 继续读取下一条消息
self->buffer_.consume(bytes_transferred);
self->DoRead();
}
});
}
void DoWrite(const std::string& message) {
ws_.async_write(boost::asio::buffer(message),
[self = shared_from_this()](beast::error_code ec, std::size_t) {
if (ec) {
// 处理错误
}
});
}
beast::websocket::stream<boost::asio::ip::tcp::socket> ws_;
beast::flat_buffer buffer_;
};
3.3 RESTful API 设计
现代即时通讯服务器通常提供 RESTful API:
-
用户认证:
- POST /api/auth/login
- POST /api/auth/logout
-
消息管理:
- POST /api/messages/send
- GET /api/messages/history
-
群组管理:
- POST /api/groups/create
- GET /api/groups/list
-
实现示例:
cpp复制void HandleApiRequest(const http::request<http::string_body>& req, http::response<http::string_body>& res) {
if (req.target().starts_with("/api/auth/login")) {
// 处理登录逻辑
HandleLogin(req, res);
} else if (req.target().starts_with("/api/messages/send")) {
// 处理消息发送
HandleSendMessage(req, res);
} else {
res.result(http::status::not_found);
res.body() = "Not Found";
}
res.prepare_payload();
}
4. 高级主题与优化
4.1 SSL/TLS 加密通信
使用 Boost.Asio 实现安全通信:
cpp复制#include <boost/asio/ssl.hpp>
class SslSession : public std::enable_shared_from_this<SslSession> {
public:
SslSession(boost::asio::ip::tcp::socket socket, boost::asio::ssl::context& ctx)
: stream_(std::move(socket), ctx) {}
void Start() {
// 执行SSL握手
stream_.async_handshake(boost::asio::ssl::stream_base::server,
[self = shared_from_this()](const boost::system::error_code& ec) {
if (!ec) {
self->DoRead();
}
});
}
private:
void DoRead() {
stream_.async_read_some(boost::asio::buffer(data_),
[self = shared_from_this()](const boost::system::error_code& ec, std::size_t length) {
if (!ec) {
// 处理加密数据
self->ProcessData(length);
self->DoRead();
}
});
}
boost::asio::ssl::stream<boost::asio::ip::tcp::socket> stream_;
std::array<char, 1024> data_;
};
4.2 协程支持
C++20 协程与 Boost.Asio 结合:
cpp复制#include <boost/asio.hpp>
#include <boost/asio/experimental/awaitable_operators.hpp>
using namespace boost::asio::experimental::awaitable_operators;
boost::asio::awaitable<void> HandleSession(boost::asio::ip::tcp::socket socket) {
try {
char data[1024];
for (;;) {
std::size_t n = co_await socket.async_read_some(
boost::asio::buffer(data), boost::asio::use_awaitable);
co_await boost::asio::async_write(
socket, boost::asio::buffer(data, n), boost::asio::use_awaitable);
}
} catch (const std::exception& e) {
std::cerr << "Session error: " << e.what() << std::endl;
}
}
boost::asio::awaitable<void> Listener() {
auto executor = co_await boost::asio::this_coro::executor;
boost::asio::ip::tcp::acceptor acceptor(executor,
{boost::asio::ip::tcp::v4(), 12345});
for (;;) {
auto socket = co_await acceptor.async_accept(boost::asio::use_awaitable);
boost::asio::co_spawn(executor,
HandleSession(std::move(socket)),
boost::asio::detached);
}
}
int main() {
boost::asio::io_context io_context;
boost::asio::signal_set signals(io_context, SIGINT, SIGTERM);
signals.async_wait([&](auto, auto) { io_context.stop(); });
boost::asio::co_spawn(io_context, Listener(), boost::asio::detached);
io_context.run();
}
4.3 性能监控与调优
-
关键指标监控:
- 连接数
- 消息吞吐量
- 响应延迟
- 内存使用
-
性能分析工具:
- gperftools
- Valgrind
- Boost.Timer
-
优化案例:
cpp复制// 优化前:每次分配新缓冲区
void DoRead() {
auto buf = std::make_shared<std::vector<char>>(1024);
socket_.async_read_some(boost::asio::buffer(*buf),
[this, buf](...) { ... });
}
// 优化后:复用缓冲区
class Session {
std::array<char, 1024> buffer_;
void DoRead() {
socket_.async_read_some(boost::asio::buffer(buffer_),
[this](...) { ... });
}
};
5. 项目部署与运维
5.1 容器化部署
使用 Docker 部署服务器:
dockerfile复制FROM ubuntu:20.04
# 安装依赖
RUN apt-get update && \
apt-get install -y build-essential cmake libboost-all-dev
# 复制源代码
COPY . /app
WORKDIR /app
# 构建项目
RUN mkdir build && \
cd build && \
cmake .. && \
make
# 运行服务
CMD ["./build/chat_server"]
5.2 系统配置优化
-
文件描述符限制:
bash复制ulimit -n 100000 -
TCP 参数调优:
cpp复制boost::asio::ip::tcp::acceptor acceptor(io_context); boost::asio::socket_base::reuse_address option(true); acceptor.set_option(option); -
内存分配优化:
cpp复制// 使用Boost的快速内存池 #include <boost/pool/pool_alloc.hpp> std::list<int, boost::fast_pool_allocator<int>> fast_list;
5.3 日志与监控
- 日志配置示例:
cpp复制#include <boost/log/trivial.hpp>
void InitLogging() {
boost::log::add_console_log(std::clog,
boost::log::keywords::format = "[%TimeStamp%]: %Message%");
boost::log::add_file_log(
boost::log::keywords::file_name = "server_%N.log",
boost::log::keywords::rotation_size = 10 * 1024 * 1024,
boost::log::keywords::format = "[%TimeStamp%]: %Message%");
}
// 使用示例
BOOST_LOG_TRIVIAL(info) << "Client connected: " << remote_endpoint;
- 监控指标导出:
cpp复制class Metrics {
public:
static Metrics& Instance() {
static Metrics instance;
return instance;
}
void IncConnections() { ++connections_; }
void DecConnections() { --connections_; }
std::map<std::string, std::string> GetMetrics() const {
return {
{"connections", std::to_string(connections_)},
{"messages", std::to_string(messages_processed_)}
};
}
private:
std::atomic<int> connections_{0};
std::atomic<int> messages_processed_{0};
};
// 在HTTP接口中暴露指标
void HandleMetricsRequest(http::request<http::string_body>& req, http::response<http::string_body>& res) {
res.result(http::status::ok);
res.set(http::field::content_type, "text/plain");
std::ostringstream oss;
for (const auto& [name, value] : Metrics::Instance().GetMetrics()) {
oss << name << " " << value << "\n";
}
res.body() = oss.str();
res.prepare_payload();
}
6. 实战经验分享
6.1 常见问题与解决方案
-
内存泄漏排查:
- 使用 Valgrind 检测内存问题
- 确保所有 shared_ptr 的循环引用被打破
- 使用 weak_ptr 中断循环引用
-
性能瓶颈定位:
cpp复制#include <boost/timer/timer.hpp> void ProcessRequest() { boost::timer::cpu_timer timer; // 业务逻辑... std::cout << timer.format() << std::endl; } -
跨平台问题:
- Windows 和 Linux 的 socket 行为差异
- 字节序处理(始终使用网络字节序传输)
- 文件路径处理(使用 Boost.Filesystem)
6.2 调试技巧
- 日志记录回调链:
cpp复制socket_.async_read_some(boost::asio::buffer(data_),
[this, self](boost::system::error_code ec, std::size_t length) {
LOG_DEBUG("Read callback entered");
if (!ec) {
LOG_TRACE("Received " << length << " bytes");
ProcessData(length);
DoRead();
} else {
LOG_ERROR("Read error: " << ec.message());
}
});
- 错误处理最佳实践:
cpp复制void HandleError(const boost::system::error_code& ec) {
if (ec == boost::asio::error::eof) {
LOG_INFO("Client disconnected gracefully");
} else if (ec == boost::asio::error::connection_reset) {
LOG_WARNING("Client connection reset");
} else {
LOG_ERROR("Unexpected error: " << ec.message());
}
// 根据错误类型决定是否重试或关闭连接
if (IsRecoverableError(ec)) {
RetryOperation();
} else {
CloseConnection();
}
}
6.3 扩展功能建议
-
消息持久化:
- 集成 Redis 作为消息缓存
- 使用 MySQL/PostgreSQL 存储历史消息
-
集群支持:
- 使用 etcd 或 ZooKeeper 进行服务发现
- 实现基于 gRPC 的节点间通信
-
消息队列集成:
- 使用 RabbitMQ 或 Kafka 处理高吞吐量消息
- 实现消息优先级和延迟队列
-
微服务架构:
cpp复制// gRPC 服务示例 service ChatService { rpc SendMessage (MessageRequest) returns (MessageResponse); rpc GetHistory (HistoryRequest) returns (stream Message); }
7. 完整项目结构参考
一个典型的即时通讯服务器项目结构:
code复制im_server/
├── CMakeLists.txt
├── include/
│ ├── common/
│ │ ├── config.h
│ │ ├── logger.h
│ │ └── utils.h
│ ├── network/
│ │ ├── session.h
│ │ ├── server.h
│ │ └── io_pool.h
│ └── service/
│ ├── auth.h
│ ├── message.h
│ └── user.h
├── src/
│ ├── main.cpp
│ ├── network/
│ │ ├── session.cpp
│ │ ├── server.cpp
│ │ └── io_pool.cpp
│ └── service/
│ ├── auth.cpp
│ ├── message.cpp
│ └── user.cpp
├── third_party/
│ └── boost/
└── tools/
├── deploy.sh
└── monitor.py
关键组件说明:
- io_pool:IO 线程池实现
- session:客户端会话管理
- server:主服务器逻辑
- service/:各种业务服务实现
- common/:公共工具类和函数
8. 构建与测试
8.1 CMake 配置示例
cmake复制cmake_minimum_required(VERSION 3.10)
project(im_server)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
find_package(Boost 1.70 REQUIRED COMPONENTS system thread)
include_directories(
${CMAKE_SOURCE_DIR}/include
${Boost_INCLUDE_DIRS}
)
add_executable(im_server
src/main.cpp
src/network/session.cpp
src/network/server.cpp
src/network/io_pool.cpp
src/service/auth.cpp
src/service/message.cpp
)
target_link_libraries(im_server
${Boost_LIBRARIES}
pthread
)
8.2 单元测试框架
使用 Boost.Test 进行单元测试:
cpp复制#define BOOST_TEST_MODULE SessionTest
#include <boost/test/included/unit_test.hpp>
#include "../include/network/session.h"
BOOST_AUTO_TEST_CASE(test_session_creation) {
boost::asio::io_context ioc;
boost::asio::ip::tcp::socket socket(ioc);
auto session = std::make_shared<Session>(std::move(socket));
BOOST_CHECK(session != nullptr);
// 测试会话开始
session->Start();
BOOST_CHECK(session->IsActive());
}
8.3 性能测试方法
-
基准测试工具:
- wrk (HTTP)
- netcat (原始 TCP)
- custom_test_client (自定义协议)
-
测试场景设计:
- 逐步增加并发连接数
- 测量不同消息大小下的吞吐量
- 长时间运行稳定性测试
-
结果分析:
bash复制# 示例输出 Connections: 1000 Messages/sec: 12500 Avg Latency: 12.5ms P99 Latency: 45.2ms Memory Usage: 250MB
9. 进阶学习资源
9.1 推荐书籍
- 《Boost.Asio C++ Network Programming》
- 《C++ Network Programming with Patterns, Frameworks, and ACE》
- 《Effective Modern C++》
9.2 在线资源
9.3 相关项目参考
10. 持续集成与交付
10.1 CI/CD 流水线配置
GitLab CI 示例:
yaml复制stages:
- build
- test
- deploy
build:
stage: build
script:
- mkdir build
- cd build
- cmake ..
- make
artifacts:
paths:
- build/im_server
test:
stage: test
script:
- cd build
- ctest --output-on-failure
deploy:
stage: deploy
only:
- master
script:
- scp build/im_server deploy@server:/opt/im_server
- ssh deploy@server "systemctl restart im_server"
10.2 版本管理策略
-
语义化版本:
- MAJOR.MINOR.PATCH
- 1.0.0 初始版本
- 1.1.0 新增功能
- 1.1.1 bug修复
-
Git 分支模型:
- master:生产代码
- develop:开发分支
- feature/*:功能开发
- hotfix/*:紧急修复
10.3 监控告警配置
Prometheus 监控示例:
yaml复制scrape_configs:
- job_name: 'im_server'
static_configs:
- targets: ['localhost:8080']
Grafana 仪表板指标:
- 活跃连接数
- 消息吞吐量
- 系统资源使用率
- 错误率
11. 安全最佳实践
11.1 认证与授权
- JWT 认证实现:
cpp复制std::string GenerateToken(const User& user) {
auto now = std::chrono::system_clock::now();
auto expires = now + std::chrono::hours(24);
jwt::builder token_builder;
token_builder
.set_issuer("im_server")
.set_subject(user.id)
.set_issued_at(now)
.set_expires_at(expires)
.set_payload_claim("role", jwt::claim(user.role));
return token_builder.sign(jwt::algorithm::hs256{secret_key});
}
- 权限检查中间件:
cpp复制bool CheckPermission(const http::request<http::string_body>& req, UserRole required_role) {
auto auth_header = req.find(http::field::authorization);
if (auth_header == req.end()) return false;
try {
auto token = jwt::decode(auth_header->value());
auto verifier = jwt::verify()
.allow_algorithm(jwt::algorithm::hs256{secret_key})
.with_issuer("im_server");
verifier.verify(token);
auto role = token.get_payload_claim("role").as_string();
return GetRoleLevel(role) >= GetRoleLevel(required_role);
} catch (...) {
return false;
}
}
11.2 数据验证
- 消息内容过滤:
cpp复制std::string FilterMessage(const std::string& input) {
static const std::regex malicious_patterns[] = {
std::regex("<script.*?>.*?</script>", std::regex::icase),
std::regex("onload=.*?\\(", std::regex::icase)
};
std::string output = input;
for (const auto& pattern : malicious_patterns) {
output = std::regex_replace(output, pattern, "");
}
return output;
}
- 速率限制:
cpp复制class RateLimiter {
public:
bool Check(const std::string& ip) {
auto now = std::chrono::steady_clock::now();
auto& record = records_[ip];
if (record.count >= limit_ &&
now - record.last_time < interval_) {
return false;
}
if (now - record.last_time >= interval_) {
record.count = 0;
}
record.count++;
record.last_time = now;
return true;
}
private:
struct Record {
int count = 0;
std::chrono::steady_clock::time_point last_time;
};
std::unordered_map<std::string, Record> records_;
int limit_ = 100; // 100次/interval
std::chrono::seconds interval_{60};
};
11.3 安全通信
- HTTPS 配置:
cpp复制boost::asio::ssl::context CreateSslContext() {
boost::asio::ssl::context ctx(boost::asio::ssl::context::tls_server);
ctx.set_options(
boost::asio::ssl::context::default_workarounds |
boost::asio::ssl::context::no_sslv2 |
boost::asio::ssl::context::single_dh_use);
ctx.use_certificate_chain_file("server.crt");
ctx.use_private_key_file("server.key", boost::asio::ssl::context::pem);
ctx.use_tmp_dh_file("dh2048.pem");
return ctx;
}
- 安全头部设置:
cpp复制void SetSecurityHeaders(http::response<http::string_body>& res) {
res.set(http::field::strict_transport_security, "max-age=31536000; includeSubDomains");
res.set(http::field::x_content_type_options, "nosniff");
res.set(http::field::x_frame_options, "DENY");
res.set(http::field::x_xss_protection, "1; mode=block");
res.set(http::field::content_security_policy,
"default-src 'self'; script-src 'self' 'unsafe-inline'");
}
12. 性能调优实战
12.1 连接池优化
数据库连接池