5 个不稳定版本

0.3.1 2024 年 5 月 21 日
0.3.0 2024 年 5 月 21 日
0.2.0 2024 年 1 月 9 日
0.1.1 2023 年 12 月 11 日
0.0.1 2023 年 9 月 18 日

#402 in 网页编程

MIT/Apache

150KB
3K SLoC

Progressive RESTful 框架,让应用开发再次变得简单。即使您还不熟悉 Rust,也可能对此感兴趣,因为它旨在尽可能地对初学者友好 - prest 允许以编写 HTML 的开发成本构建全栈跨平台应用程序。教程可在博客中找到,该博客也是使用 prest 构建的。请注意,它仍然是 alpha 版本,仅推荐用于宠物项目和培训,因为预计会有许多破坏性变更。如果您想了解其发展方向,请在 GitHub 上给它点个星!

与 Laravel、Rails、Nextjs 等许多其他产品竞争并不容易,但我一直想要一个框架,它能够在常见开发需求中实现简单性,并允许 任何 自定义/优化而不必切换语言。 Rust 提供了构建服务器、客户端、人工智能、区块链、操作系统内核等所需的一切方法,同时可以说是最 可靠实用的语言。多亏了底层众多惊人的依赖项,prest 已经提供了一整套功能

快速入门 - 创建默认的 Rust 项目,添加 prest 依赖项,从其中大量 use 所有内容,调用 init! 宏并添加您的应用程序逻辑。无需大量样板项目,无需自定义 CLI 工具。

use prest::*;
fn main() {
    init!();
    ...
}

服务器 - 高性能、并发、直观的路由。包括强大的中间件 API、简单的提取器从请求中获取信息处理程序所需的信息,以及灵活的返回类型。只需 run 您的路由器,其他所有内容将自动配置。

route("/", get("Hello world")).run()

UI - html! 宏用于 Rust'y 模板,使用 Tailwind 和 Daisyui 轻松进行内联样式,使用 htmx 简单地进行客户端-服务器交互。使用非常少的 JS 实现平滑的 UX。

html!{ 
    nav."navbar" {
        input."input input-bordered w-full" name="search" 
            hx-post="/search" hx-target="#search-results" {} 
    }
    ...
    main {
        div#"#search-results" {"Response will be placed here!"}
    }
}

数据库 - 嵌入式 SQL 数据库,无需运行单独的服务即可工作。基于常见的 Rust 结构自动生成模式,包括查询构建器和辅助函数。只需将其添加到 init! 宏中,即可确保其已初始化。

#[derive(Table, serde::Deserialize)]
struct Todo {
    id: Uuid,
    task: String,
    done: bool,
}
...
init!(tables Todo/*, OtherTable, ... */)
...
Todo::find_all()
Todo::find_by_task("Buy milk")
Todo::select().filter(col("done").eq(true)).order_by("task").values()
todo.save()
todo.update_task("Buy milk and bread")
todo.check_task("Buy milk and bread")
todo.remove()

仅需 serdeDeserialize 派生即可在 ... 中启用数据库编辑器。

管理面板 - 收集请求/响应、日志的过滤统计信息,并为所有已初始化的表提供读写GUI。虽然博客有意向演示目的开放访问,但默认情况下,所有以 /admin 开头的内置和应用程序路由都受到...

身份验证 - 基于密码和OAuth/openID的会话和用户管理。持久化在内置数据库中,可以通过引导用户到预定义的路由来启动,并可以使用提取器检索当前的认证/用户信息。

html!{ 
    // for username/password flow
    form method="POST" action=(LOGIN_ROUTE) { ... }
    // for oauth flow
    a href=(GOOGLE_LOGIN_ROUTE) {"Login with Google"}
}
...
route("/authorized-only", get(|user: User| async {"Hello world"}))
route("/optional", get(|auth: Auth| async {"auth.user is Option<User>"}))

要启用它,您需要 prest 的 auth 功能。

prest = { version = "0.3", features = ["auth"] }

请注意,目前如果没有此功能,面板将是公开的,因此您可以在 博客的 中查看。

部署 - prest 支持基于 Docker 的 1 点击构建-上传-启动部署流程,适用于跨平台编译,并自带基于 Let's Encrypt 自动配置的 TLS。要使其工作,您需要在 Cargo.toml 中指定域名并提供凭证。

[package.metadata]
domain = "prest.blog"
# add when starting app locally in the shell or in the .env file
SSH_ADDR=123.232.111.222
SSH_USER=root
SSH_PASSWORD=verystrongpassword

只需在管理面板中点击 Deploy 按钮!您很可能会希望为用户提供更原生应用般的体验,因此...

PWA - 您可以将一些服务器和UI代码构建到基于WASM的服务工作者中,并构建一个渐进式Web应用程序,以便用户可以安装并使用一些离线路由。要使其工作,您需要将主机专用代码与共享主机+客户端代码分离,在SW中初始化共享路由,添加 wasm-bindgenprest-build 依赖项,添加一个小型构建脚本,并将编译的资产嵌入到主机中。

#[wasm_bindgen(start)]
pub fn main() {
    shared_routes().handle_fetch_events()
}
...
wasm-bindgen = "0.2"
[build-dependencies]
prest-build = "0.3"
use prest_build::*;
fn main() {
    build_pwa(PWAOptions::default()).unwrap();
}
embed_build_output_as!(BuiltAssets);
...
router.embed(BuiltAssets)

默认情况下,它将在 --release 模式下仅运行完整的PWA构建,以避免减慢常规开发,但您可以使用 PWA=debug 环境变量来强制执行完整构建。如果PWA体验不足以满足您的需求,还有另一个选项...

原生 - 使用webview运行离线优先应用的主机功能。有点像Electron,但二进制文件更小、速度更快。基于与Tauri相同的库,但用于以Rust为先的应用。要为桌面构建,只需像这样启用webview功能

prest = { version = "0.3", features = ["webview"] }

但目前对于移动平台,您需要做一些 工作

构建工具 - 除了PWA prest-build 还包括一些可选功能 - sasstypescript,它们允许对typescript/js和sass/scss进行转译和捆绑。

// paths relative to the build script
bundle_sass("path to main css/scss/sass file")
bundle_ts("path to main ts/js file")

它们的编译版本可以像PWA资产一样嵌入,还有一个类似但更灵活的宏 embed_as!,它可以用任意文件夹和文件使用,这个宏旨在在调试构建中按需从驱动器读取文件以避免减慢编译,但在发布构建中它将它们的内嵌入到二进制文件中,您将获得一个包含整个应用的单个文件,以便于读取和加快速度。这些宏生成Rust结构,提供对文件内容和元数据的访问,就像博客正在处理以渲染文档

embed_as!(ExamplesDocs from "../" only "*.md");
embed_as!(ExamplesCode from "../" except "*.md");

或可以很容易地使用 .embed(StructName) 将其嵌入到路由器中。

还有一个基于Rust的cron替代品,用于作为后台任务启动,就像这样

RT.every(5).seconds().spawn(|| async { do_smth().await })
RT.every(1).day().at(hour, minute, second).spawn(...) 

使用 trace!debug!info!warn!error! 宏进行日志记录、优雅关闭机制和许多其他实用工具。

入门

如果您还不熟悉 Rust,我强烈建议您查看《Rust 书籍》——绝对是最全面的指南,包含数十种语言的交互式示例!此外,我还建议您浏览一下异步书籍的前三章,以了解 Rust 中并发工作的整体情况。

Prest 教程是从基础开始,然后逐渐添加更多功能。

  1. Todo = 仅需约 50 行代码的基本全栈待办事项应用
  2. PWA = 1 + PWA 功能和离线视图,约 80 行代码
  3. Auth = 2 + 用户名和密码以及 Google 验证,约 110 行代码
  4. Sync = 3 + 客户端之间的同步,约 160 行代码

还有其他使用替代数据库的待办事项示例——通过 seaormdiesel 使用 postgres,通过 sqlxturbosql 使用 sqlite,mongoredis。此外,还有一些示例展示了如何使用 prest 与 Web 开发中不常见的科技:网络爬虫大型语言模型和一个区块链智能合约

要本地运行,您需要最新的稳定版 rust 工具链。我还建议立即为您的首选 IDE 设置 rust-analyzer。要从克隆的 prest 仓库中构建和启动任何示例,请使用 cargo run -p EXAMPLE-NAME。或者,只需将所选示例的代码从教程中复制到本地文件中,并使用 cargo run 运行它。某些示例需要额外的设置和凭据,这些在它们的文档中有说明。

接下来是什么

这是一个爱好项目,计划随时可能改变,但我可能会做或考虑以下事情

  • 将更详细的日志写入文件,并为其创建一个浏览器
  • 博客中的评论?需要更多互动性
  • 允许为不同的非 200 响应代码设置模板?或者只是基于 htmx 的处理?
  • 将 maud 适配到与 tailwind 和 htmx 一起使用?
  • 添加类似 storybook 的功能
  • 重新编写爬虫和区块链示例
  • SQL 转义
  • 调试 SW wasm 问题,改进默认清单

在 prest 发布之前,还有一些长期需要或希望拥有的东西

  • 等待 axum 和 sled 等最重要依赖的稳定版本
  • 为 rust 编译器的并行前端和 cranelift 后端添加功能以加快构建速度
  • 稳定和异步迭代器以及其他基本并发 std apis 的支持
  • 提供更多可选配置以提高灵活性
  • 找到一种方法将/导出为 prest,以避免需要其他依赖项
  • 添加更多示例,如 i18n,高度交互式的 UI,本地移动构建,基于 webgpu 的现代语言模型等

依赖项

~6–66MB
~1M SLoC