3 个不稳定版本
新 0.2.0-alpha.1 | 2024 年 8 月 18 日 |
---|---|
0.2.0-alpha.0 | 2024 年 6 月 2 日 |
0.1.0 | 2022 年 9 月 21 日 |
#284 in 网络编程
用于 rama-cli
3.5MB
55K SLoC
🦙 Rama (ラマ) 是一个为 🦀 Rust 语言设计的模块化服务框架,用于移动和转换您的网络数据包。关于创建拉马的原因,可以阅读 “为什么选择拉马”章节。
拉马是异步优先的,使用 Tokio 作为其 唯一 的异步运行时。请参考 位于 /examples
目录中的示例,以获得如何将其用于您的目的的灵感。
💡 如果您的组织依赖于 Rama (ラマ) 进行运营,我们邀请您考虑成为赞助商 💖。通过支持我们的项目,您将帮助确保其持续的发展和成功。有关赞助机会的更多信息,请参阅下面的 “赞助商”部分 或直接联系我们在 [email protected]。
此框架内置了 🔋 电池,让您完全自由地构建您想要的中间件和服务,而无需重复“通用”
分类 | 支持列表 |
---|---|
✅ 传输 | ✅ tcp ⸱ 🏗️ udp (2) ⸱ ✅ 中间件 |
✅ http | ✅ auto ⸱ ✅ http/1.1 ⸱ ✅ h2 ⸱ 🏗️ h3 (2) ⸱ ✅ 中间件 |
✅ 网络服务器 | ✅ 文件系统(fs) ⸱ ✅ 重定向(redirect) ⸱ ✅ 动态路由器(dyn router) ⸱ ✅ 静态路由器(static router) ⸱ ✅ 处理器提取器(handler extractors) ⸱ ✅ k8s健康检查(k8s healthcheck) |
✅ HTTP 客户端(client) | ✅ 客户端(client) ⸱ ✅ 高级API(high level API) ⸱ ✅ 代理连接(Proxy Connect) ⸱ ❌ Chromium Http (3) |
✅ TLS (tls) | ✅ Rustls ⸱ ✅ BoringSSL ⸱ ❌ NSS (3) |
✅ DNS(dns) | ✅ DNS解析器(DNS Resolver) |
✅ 代理协议(proxy protocols) | ✅ 代理协议(PROXY protocol) ⸱ ✅ HTTP代理(http proxy) ⸱ ✅ HTTPS代理(https proxy) ⸱ 🏗️ SOCKS5 (1) ⸱ 🏗️ SOCKS5H (1) |
🏗️ 网络协议 | 🏗️ Web Sockets (WS) (2) ⸱ 🏗️ WSS (2) ⸱ ❌ Web Transport (3) ⸱ ❌ gRPC (3) |
✅ 异步方法特征服务(async-method trait services) | ✅ 服务(Service) ⸱ ✅ 层(Layer) ⸱ ✅ 上下文(context) ⸱ ✅ 动态调度(dyn dispatch) ⸱ ✅ 中间件(middleware) |
✅ 指标(telemetry) | ✅ 跟踪(tracing) ⸱ ✅ opentelemetry ⸱ ✅ HTTP指标(http metrics) ⸱ ✅ 传输指标(transport metrics) |
✅ 上游代理(upstream proxies) | ✅ 内存代理数据库(MemoryProxyDB) ⸱ ✅ L4用户名配置(L4 Username Config) ⸱ ✅ 代理过滤器(Proxy Filters) |
🏗️ 用户代理(User Agent) | 🏗️ HTTP仿真 (1) ⸱ 🏗️ TLS仿真 (1) ⸱ ✅ 用户代理解析(UA Parsing) |
✅ 工具(utilities) | ✅ 错误处理(error handling) ⸱ ✅ 优雅关闭(graceful shutdown) ⸱ 🏗️ 连接池 (2) ⸱ 🏗️ IP2Loc (2) |
🏗️ TUI(文本用户界面) | 🏗️ 流量记录器 (2) ⸱ 🏗️ curl导出 (2) ⸱ ❌ 流量拦截 (3) ⸱ ❌ 流量回放 (3) |
✅ 二进制文件 | ✅ 预构建的二进制文件(prebuilt binaries) ⸱ 🏗️ 代理配置 (2) ⸱ ✅ HTTP客户端 ⸱ ❌ WASM插件 (3) |
🏗️ 数据抓取 | 🏗️ HTML处理器 (2) ⸱ ❌ JSON处理器 (3) |
❌ 浏览器 | ❌ JS 引擎 (3) ⸱ ❌ Web API 模拟 (3) |
🗒️ 脚注
- (1) 属于
v0.2.0
里程碑 (预计:2024 年第三季度中)- (2) 属于
v0.3.0
里程碑 (预计:2024 年第三季度末)- (3) 目前没有计划,但已纳入我们的考虑范围内。如果您迫切需要此功能,请 提交问题。请提供充分的动机/理由,并考虑 成为赞助商 以帮助加速其优先级。
Rama 的主要重点是帮助您开发 代理
💡 请查看 Rama 书籍中的 "代理简介" 章节以了解更多关于不同类型代理的信息。如果您是代理开发新手,这可能有所帮助。
扭曲代理支持包含 用户代理 (UA) 模拟功能。通过使用 rama-fp
提取的模式和数据,实现了模拟。该服务在 https://fp.ramaproxy.org 公开提供,由我们的赞助商主机 https://fly.io/ 实现。
🔁 另一个公开提供的服务是 https://echo.ramaproxy.org/。与指纹服务相比,它面向开发者,允许您发送任何您希望的 HTTP 请求,以便在发送请求时了解服务器从您那里接收的 TLS 信息和 HTTP 请求信息。
curl -XPOST 'https://echo.ramaproxy.org/foo?bar=baz' \ -H 'x-magic: 42' --data 'whatever forever'
您可以在构建扭曲的 HTTP 请求时自由使用它,但请适度使用。如果您有任何改进服务的想法,请通过 提交问题 告诉我们。
使用
rama
二进制文件,您还可以自己运行echo
和fp
服务,本地或作为外部面对服务的网络服务。如果您计划向 echo 服务发送大量流量,请运行您自己的 echo 服务,而不是使用
echo.ramaproxy.org
。
BrowserStack 通过提供真实设备上的跨平台浏览器自动化测试来赞助 Rama,该服务使用公共指纹服务来帮助在 HTTP 和 TLS 层面上进行自动指纹收集。按设计,我们不考虑 Tcp 和 Udp 指纹。
除了代理外,Rama 还可用于开发 Web 服务 和 HTTP 客户端。
- 通过阅读 https://ramaproxy.org/book 中的 Rama 书籍了解更多信息;
- 或者查看Rama框架的文档:https://docs.rs/rama;
- 边缘文档(主分支)可以在https://ramaproxy.org/docs/rama找到。
📖 Rama的完整文档、参考材料和背景资料可以以“rama书”的形式在https://ramaproxy.org/book找到。
💬 加入我们的Discord频道#rama
,链接:Discord。在这里可以提问、讨论想法以及了解Rama如何为您所用。
⌨️ | rama
二进制文件
rama
二进制文件允许您使用Rama的大部分功能,而无需自己编写代码。它包含用于CLI的工作HTTP客户端,模拟User-Agent并提供其他实用工具。它还包含IP/Echo服务。
它还允许您运行一个配置满足您需求的rama
代理。
更多关于rama
二进制文件及其安装信息,请访问https://ramaproxy.org/book/binary/rama。
🧪 | 实验
🦙 Rama(ラマ)在可预见的未来被视为实验性软件。同时,我们和他人已在生产中使用。这很好,因为它为我们提供了新的视角和数据,以进一步改进和扩展框架。但这意味着,在0.2之后,还将有多个不向后兼容的版本发布。
同时,Rust的异步生态系统也在成熟,预计2024年也将迎来2024年的年终礼物。不言而喻,我们不会随意更改设计或故意破坏。核心设计现在也已经非常明确。但必须说,还有很多需要改进和解决的问题。您的生产使用和其他用户的反馈对此有很大帮助。因此,如果您使用Rama,请通过Discord、电子邮件或GitHub问题告诉我们您的反馈。
👉 如果您是使用Rama的公司或企业,或者甚至是个体用户,为了商业目的使用Rama,请考虑成为商业/企业订阅者。这有助于使开发周期保持可持续,同时也对您有益。作为您的好处之一,我们还可以协助您在破坏性发布之间进行迁移。对于企业用户,我们甚至可以代表您自己开发集成代码库中的PR。这对每个人都是双赢。💪
🏢 | 代理示例
- /examples/tls_termination.rs:启动一个迷你手工HTTP服务器以及一个TLS终止代理,将明文流转发到第一个。
- /examples/tls_termination.rs:启动一个迷你手工HTTP服务器以及一个TLS终止代理,将明文流转发到第一个。
- /examples/mtls_tunnel_and_service.rs:如何使用Rama进行mTls(手动Tls,客户端也需要证书)的示例,以及如何使用此概念提供隧道服务的示例;
- /examples/http_connect_proxy.rs:启动一个最小的HTTP代理,它接受http/1.1和h2连接,并将它们代理到目标主机。
🌐 | 网络服务
开发代理是Rama(ラマ)的主要关注点。但它也可以用于开发网络服务,用于提供网页、Http API和静态内容。这带来了与使用Rama开发代理时相同的许多好处。
- 使用异步方法特质;
- 使用扩展以及强类型状态重用类似Tower的中间件;
- 能够从传输层(Tcp、Udp)到Tls和Http,全面控制您的Web堆栈;
- 如果您只关心Http层,那也完全没问题。
- 相信您的传入应用程序Http数据没有被修改(例如,Http头大小写和顺序保持不变);
- 轻松在请求层和高层功能上开发您的服务,选择由您决定,并可组合使用。
以下是一些您可能使用rama结合您的代理服务构建的Web服务示例
- 一个k8s健康服务(/examples/http_k8s_health.rs);
- 一个指标暴露服务;
- 一个最小化的api服务(例如,用于暴露设备配置文件或证书);
- 一个图形界面/控制面板;
📖 在Rama书中了解更多关于开发Web服务的信息:https://ramaproxy.org/book/web_servers.html。
🌐 | Web服务示例
以下是一些没有花哨功能的底层Web服务示例
- /examples/http_listener_hello.rs:这是如何提供一个无需端点或其他任何东西的根服务的最基本示例(例如,对于一些与健康服务或指标暴露相关的用例来说足够好);
- /examples/http_health_check.rs是一个更简化的健康检查服务示例,它对任何传入请求都返回200 OK。
- /examples/http_service_hello.rs:与前面的示例类似,但展示了您还可以在将数据传递给Http服务之前对底层传输(TCP)层进行操作;
还有一个现成的webservice,可以用作代理k8s工作负载的健康服务
- /examples/http_k8s_health.rs:内置的web服务,可以作为部署为k8s部署的代理的k8s健康服务使用;
以下是一些使用请求/状态提取器和IntoResponse转换器的高级概念示例,这些概念您在axum
中已经熟悉,同样也适用于rama
服务
- /examples/http_key_value_store.rs:一个Web服务示例,展示了如何使用
Rama
实现键值存储Web服务; - /examples/http_web_service_dir_and_api.rs:一个Web服务示例,展示了如何构建一个Web服务来提供包含XHR API的网站;
对于类似生产环境的Web服务示例,您还可以阅读rama cli fp
cmd源代码。这是Rama指纹服务背后的webservice,该服务由🦙 Rama(ラマ)的维护者使用,以生成Http和TLS层的UA仿真数据。它不是用来指纹人类或用户的。相反,它是用来帮助自动化过程看起来像人类。
💡 此示例展示了如何使用
match_service
宏来创建一个无Box
的服务路由器。此方法的其他示例可以在http_service_match.rs示例中看到。
🧑💻 | Http客户端
在《rama书》中,你可以阅读并学习到,Rama架构的一个大支柱是基于服务概念构建的。一个Service
将用户定义的State
(例如包含你的数据库池)和一个Request
作为输入,并使用它来提供Response
或Error
。这样的Service
可以直接产生响应(也称为☘️Leaf服务)或者将请求和状态传递给它包装的内部Service
(所谓🍔Middlewares)。
这是一个强大的概念,最初由Tower生态系统引入到Rust中,允许你以模块化和简单的方式构建满足你需求的复杂堆栈。更酷的是,这对客户端和服务器都适用。
Rama提供了一个HttpClient
,它通过网络发送你的Http Request
,并在接收到并读取响应或错误时返回。结合Rama提供的众多层(中间件)以及你可能开发的一些,可以创建一个满足你需求的强大Http客户端。
作为🍒蛋糕上的樱桃,你可以在你的Rust模块中导入HttpClientExt
特性,以便能够使用高级API轻松构建和发送请求来使用你的Http客户端Service
堆栈。
🧑💻 | Http客户端示例
💡完整的“高级”示例可以在/examples/http_high_level_client.rs找到。
use rama::http::client::HttpClientExt;
let client = (
TraceLayer::new_for_http(),
DecompressionLayer::new(),
AddAuthorizationLayer::basic("john", "123")
.as_sensitive(true)
.if_not_present(),
RetryLayer::new(
ManagedPolicy::default().with_backoff(ExponentialBackoff::default()),
),
).layer(HttpClient::default());
#[derive(Debug, Deserialize)]
struct Info {
name: String,
example: String,
magic: u64,
}
let info: Info = client
.get("http://example.com/info")
.header("x-magic", "42")
.typed_header(Accept::json())
.send(Context::default())
.await
.unwrap()
.try_into_json()
.await
.unwrap();
⛨ | 安全性
这个crate使用#![forbid(unsafe_code)]
来确保所有内容都是在100%安全的Rust中实现的。
🦀 | 兼容性
Rama(ラマ)主要在MacOS M-Series机器上开发,并在各种Linux系统上运行生产环境。没有Windows支持,并且我们也没有在该平台上进行测试。
platform | tested | test platform |
---|---|---|
MacOS | ✅ | MacOS Apple Silicon(开发者笔记本电脑)和macos-12 Intel(《GitHub Action) |
Linux | ✅ | Ubuntu 22.04(《GitHub Action) |
如果你在设置/平台上遇到兼容性问题,请打开一个票据。我们的目标不是支持世界上所有可能的平台,但我们确实希望尽可能多地支持。
最小支持的Rust版本
Rama的MSRV是1.75
使用 GitHub Actions 我们还测试了 在该版本上 rama
是否仍然可以在 rust 的稳定版和测试版上工作。
🧭 | 路线图
请参阅 https://github.com/plabayo/rama/milestones 了解路线图上的内容。下个版本有没有你真正希望加入的功能?请 创建一个功能请求 并如果可能的话 成为赞助商。
📰 | 媒体报道
Rama (0.2
) 在 2024 年 5 月 19 日的 Rustacean 播客中有所介绍,可在 https://rustacean-station.org/episode/glen-de-cauwsemaecker/ 上收听。在这个播客中,Glen 解释了 Rama 的历史、为什么存在以及如何使用等内容。
💼 | 许可证
本项目同时受 MIT 许可证 和 Apache 2.0 许可证 的双重许可。
👋 | 贡献
🎈 感谢您的帮助,让我们改进项目!我们很高兴有您加入!我们有一个 贡献指南,以帮助您参与 rama
项目。
贡献通常来自那些已经知道他们想要什么的人,无论是他们遇到的错误修复,还是他们缺少的功能。如果还没有,请务必创建一个工单。
然而,可能您还不知道具体要贡献什么,但仍然想帮忙。为此,我们感谢您。您可以查看开放的问题,特别是
good first issue
:适合初学者参与rama
代码库的问题;easy
:被认为是简单的问题;mentor available
:我们提供指导的问题;low prio
:优先级低的问题,没有立即的压力要快速完成,如果您想帮忙但时间有限,非常适合;
一般来说,任何未分配的问题都可以由其他人选择。如果您计划处理它,请务必在工单中沟通,以避免多人尝试解决相同的问题。
💡 一些问题有
needs input
标签。这意味着问题尚未准备好开发。首先,在开始处理问题之前,您应该始终寻找与 rama 维护者的意见一致。然而,这些needs input
问题还需要进行前期研究和开发工作
- 添加和讨论缺失的知识或其它不清楚的地方;
- 确定解决方案的优缺点(以及如果我们选择不解决该问题会怎样);
- 讨论和头脑风暴可能的实现、期望的功能、后果、好处等;
只有在完成前期研究和确认一致后,才能开始实现功能。
如果您想为这个项目贡献力量,但您目前还不知道如何使用Rust编程,您可以从学习Rust开始,以尽快为rama
做出贡献为目标。您可以使用 "Rust 101学习指南" 作为您的学习伴侣。Glen也可以作为导师或教师为您提供付费的一对一课程和其他类似的咨询服务。您可以在 https://www.glendc.com/ 找到他的联系方式。
贡献
除非您明确声明,否则您提交给 rama
的任何贡献,将同时以MIT和Apache 2.0协议授权,没有任何附加条款或条件。
致谢
特别感谢所有参与开发、维护和支持Rust编程语言、Tokio生态系统以及所有其他依赖的crate的人。这也包括Hyper及其生态系统,没有这些项目,Rama将无法存在。Rama的核心http模块是hyper
的专门分支,并使用底层的h2
和h3
crate作为依赖。
额外的赞誉也属于Axum,我们从其中借鉴了想法和代码,因为它是一个与Rama希望成为的软件类型非常吻合的项目,但用于不同的目的。我们也向Tower及其发明者,以及所有帮助它每天运行的人和生物表示敬意。我们的服务概念来源于Tower,并且我们的许多层是Tower的分支,根据需要或愿望进行了调整。
也要向这些生态系统周围和其中的在线社区表示额外的敬意。他们是聚集的好地方,总是友好和乐于助人。谢谢。
💖 | 赞助商
Rama是完全免费的、开源软件,需要大量的努力和时间来开发和维护。
您可以通过在polar.sh/plabayo支付每月订阅费来成为Rama的定期财务贡献者。如果您希望解决特定github问题或喜欢通过该平台资助问题,也可以这样做。一次性捐赠也是可能的,并且非常受欢迎。
或者,您也可以通过Github Sponsors成为(每月订阅)赞助商或一次性捐赠。对于一次性捐赠,您也可以使用"Buy me a Coffee"或"Paypal Donations",如果您更习惯于使用这些方式之一。
赞助商帮助我们继续维护和改进rama
,以及其他自由和开源(FOSS)技术。它还帮助我们创建教育内容,例如https://github.com/plabayo/learn-rust-101,以及其他开源库,如https://github.com/plabayo/tokio-graceful和https://venndb.rs。
在投入了大量无偿的开发者时间,如项目 rama
一样,我们还有许多成本,包括从托管到Docker的服务,以及开发工具和自动化处理。所有这些都需要金钱。
赞助商将获得优惠,并且根据您的常规贡献,您还可以依赖我们提供支持和咨询。
最后,您也可以通过在 https://plabayo.threadless.com/ 购买 Plabayo <3 ラマ
merchandise 🛍️ 来支持我们。
Rama 赞助商
我们想对以下赞助商表示衷心的感谢,他们为 Rama(ラマ)的开发提供了资金。如果您有兴趣成为赞助商,可以通过成为 赞助商 来实现。一次性付款可通过 GitHub 以及 "Buy me a Coffee" 进行。如果您更倾向于使用 PayPal,也可以通过 "Paypal Donations" 进行一次性或每月的财务捐赠。
如果您希望通过其他方式为我们提供财务支持,请通过发送电子邮件至 [email protected] 与我们开始对话。
高级合作伙伴
Rama(ラマ)包含了 Http/Tls 模拟数据,这是通过 BrowserStack 使用真实设备为所有主要平台和浏览器收集的。它每天自动进行此操作,使用的是我们托管在 fly.io 上的公共指纹识别服务 我们的公共指纹识别服务。
我们对这两家赞助商赞助的这些云资源表示感激。
专业服务
🤝 企业支持、软件定制、集成、专业支持、咨询和培训可通过发送电子邮件至 [email protected] 预约。或者您可以在 polar.sh/plabayo 获取完整的企业订阅。
这类合同是您支持项目的另一种方式,同时也能满足您自身的需求和目的。
Rama 以 MIT 和 Apache 2.0 许可证双重授权,因此您可以自由地用于任何目的,包括商业目的,修改源代码。尽管如此,如果您最终将其用于商业目的,我们将非常欢迎您考虑成为项目的赞助商。
🌱 | 替代方案
虽然有一些用 Rust 编写的代理,但只有两个 Rust 框架是专门为代理目的而设计的。其他所有代理代码库都是单用途代码库,其中一些甚至仅用于学习目的。或者实际上是通用的 http/web 库/框架,它们作为附加功能提供代理功能。
Cloudflare 已经在过去的几年里一直在开发一个代理服务框架,名为 pingora
,并在 2024 年 2 月 28 日开源了它。
Rama 并非适合所有人,但我们确实希望它适合您。如果不适合,请考虑尝试 pingora
,它可能是您的下一个最佳选择。
其次,字节跳动(ByteDance)有一个用 Rust 编写的开源代理框架,名为 g3proxy
,它可以开发正向和反向代理。
❓| 常见问题解答
可在 https://ramaproxy.org/book/faq.html 找到。
⭐ | 星标
依赖关系
~142MB
~3.5M SLoC