Rust 里的 Box 到底是什么

学 Rust 时,Box<T> 很容易被一句话带过:它可以把数据放到堆上。 这句话没错,但如果只记住这一句,后面看到 Box<dyn Trait>、Box<List>、Pin<Box<T>>、Box::leak 时,还是会觉得它像一个突然冒出来的语法补丁。 更好的理解方式是:Box<T> 不是“逃离所有权系统”的工具,而是 Rust 所有权系统里最基础的一种拥有型指针。它让一个值住在堆上,同时让所有权仍然清清楚楚地归某个变量管理。 先看 Box 解决了什么问题 普通变量通常可以这样理解: let n = 42; n 这个值本身就放在当前栈帧里。栈很快,进入函数时分配,函数返回时回收,生命周期也很清楚。 但有些场景光靠栈不够舒服: 一个类型递归地包含自己,编译器算不出它的大小。 你想把不同具体类型放进同一个集合,只要求它们实现同一个 trait。 一个值很大,你希望移动时只移动一个指针。 某些 API 需要一个固定地址的拥有型对象,比如配合 Pin 使用。 这时 Box<T> 就出现了。 let n = Box::new(42); 可以把它粗略想成这样: 栈上变量 n -> 保存一个指针 -> 指向堆上的 42 Box<T> 本身在栈上,里面保存指向堆数据的指针。真正的 T 在堆上。变量离开作用域时,Box<T> 会自动释放堆上的 T。 所以 Box<T> 同时有两个特点: 它是指针,可以间接访问堆上的值。 它拥有这个值,离开作用域时负责释放它。 这和 C 里的裸指针很不一样。你不用手写 free,也不能随便复制出多个拥有者。Rust 仍然会检查所有权、移动和借用。 最基本的用法:Box::new 创建一个 Box<T> 最常见的方式是 Box::new: fn main() { let name = Box::new(String::from("cloudside")); println!("{name}"); } 这里 String 这个值由 Box 放到堆上管理,name 是一个拥有它的 Box<String>。注意,String 自己内部还会管理一块字符串缓冲区;这里说的是 String 这个三字段结构本身的位置。 ...

May 24, 2026 · 5 min · Icyyan

用 Pingora 写一个最小反向代理,并把它部署起来

Cloudflare 开源 Pingora 之后,很多人会问:它能不能替代 Nginx?如果问题只是“能不能把请求转发到后端服务”,答案是能,而且几十行 Rust 就够了。但 Pingora 不是一个读取 nginx.conf 的服务器,它更像一套用来写代理、网关和网络服务的 Rust 框架。 这篇只做一件事:用 Pingora 写一个最小反向代理,让 http://127.0.0.1:6188/ 转发到本机的 127.0.0.1:3000,然后把这个二进制按服务方式部署起来。 本文示例版本核对时间:2026-05-17。示例使用 pingora = "0.8"。 先看等价的 Nginx 配置 如果用 Nginx,最小反代大概长这样: server { listen 6188; location / { proxy_pass http://127.0.0.1:3000; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto http; } } Pingora 的思路不一样。你不是写配置块,而是实现 ProxyHttp trait:请求进来以后,代码决定它要转发到哪里,转发前要改哪些请求头,最后日志怎么记。 创建项目 cargo new mini-pingora-proxy cd mini-pingora-proxy Cargo.toml: [package] name = "mini-pingora-proxy" version = "0.1.0" edition = "2021" [dependencies] async-trait = "0.1" env_logger = "0.11" log = "0.4" pingora = { version = "0.8", features = ["proxy"] } 这里用的是 pingora 聚合 crate,并启用 proxy feature。Pingora 没有默认打开所有能力;如果后面要做负载均衡,需要再启用 lb;如果要监听 HTTPS 或连接 HTTPS upstream,还要选择对应的 TLS feature,比如 openssl、boringssl、s2n 或实验性的 rustls。 ...

May 17, 2026 · 4 min · Icyyan

Pingora 深度解析:为什么 Cloudflare 用 Rust 重写了 Nginx 时代的代理架构

Cloudflare 公开 Pingora 时,最抓眼球的数字是:在相同流量下,新的代理系统比旧系统少用了约 70% CPU 和 67% 内存。 看到这个数字,很多人的第一反应可能是:是不是 Nginx 不行了?是不是 Rust 天生就比 C 快很多? 都不是。 我们真正要回答的是:Cloudflare 为什么会觉得原来的 NGINX/OpenResty 代理不够用了?Pingora 又改掉了哪些最贵的地方? 后面就顺着这个问题往下走。先看 Pingora 是什么,再看 Nginx 在普通场景里为什么很好用,最后再看 Cloudflare 这种规模下,连接池、线程模型和业务逻辑会怎样把成本放大。 可以先带着三句话往下读,后面会一层层展开: Cloudflare 替换的是他们内部深度改造过的 NGINX/OpenResty 代理,不是说 Nginx 在所有场景下都慢。 Pingora 开源版更像“用 Rust 写代理服务的工具箱”,不是一个直接读取 nginx.conf 的 Nginx 替代品。 重点不是“Rust 打败 Nginx”,而是连接复用、线程共享和复杂代理逻辑这些具体问题。 1. Pingora 不是一个新的 Nginx 如果你平时用 Nginx,可能会自然地把 Pingora 想成“另一个服务器软件”。但这样理解会有点偏。 Pingora 更像一套用 Rust 写代理服务的工具箱。它帮你处理连接、TLS、HTTP 协议、负载均衡、连接池、优雅升级这些通用能力;你的业务逻辑则写在 Rust 回调里。 它不是单个二进制 Web 服务器,而是一组 crate: crate 作用 pingora-core 底层协议、服务运行、监听器、连接器、优雅升级 pingora-proxy HTTP 代理生命周期和 ProxyHttp 回调接口 pingora-pool 高并发连接池 pingora-runtime Tokio runtime 封装,支持 work-stealing 与 no-steal 模式 pingora-load-balancing 负载均衡、健康检查、选择算法 pingora-cache / pingora-memory-cache 缓存相关能力 这些名字不用急着都记住。先有一个印象就够了:Pingora 把“写代理服务”拆成了一组可以组合的 Rust 库。 ...

May 17, 2026 · 5 min · Icyyan