rust web框架rocket指南——概要

概要

Rocket 提供最基础的架构来构建rust服务端应用:剩下的取决于你自己。简而言之,Rocket提供路由,请求前置处理和相应后置处理。至于,请求前置如何处理,相应后置如何处理,请求如何处理,都是你的业务代码决定的。

生命周期

Rocket的主要任务时监听新来的web请求,分发这些请求到业务代码,并且返回响应到客户端。我们把从请求到响应的过程叫做生命周期。我们把生命周期总结为一下几个步骤:

  1. 路由
    Rocket 会把新来的HTTP请求解析为你的代码可以操作的rust结构。并且通过匹配你程序中声明的路由属性,来检测,应该调用那个一个处理器。
  2. 验证
    Rocket在匹配了路由以后就会对请求的数据做类型及有效性的验证。如果验证失败,则Rocket会把请求转到下一个匹配的路由,或者直接调用失败处理器。
  3. 处理器
    请求的数据被验证成功之后,会作为参数来调用绑定在路由上的处理器。作为应用的主要逻辑,在调用结束后,会返回一个响应。
  4. 响应
    返回的响应也是被处理过的。Rocket 会生成合适的HTTP响应并且发送到客户端。这样一个生命周期就结束了。Rocket继续监听新的请求。并为每个请求创建一个生命周期。

这个章节剩余的部分会详述路由部分和Rocket分发请求到请求处理器所需要的组件。之后的章节会详述请求、响应部分和Rocket的其它组件。

路由

Rocket应用都是以路由和处理器为中心。路由由下列组成:

  • 一组参数来匹配新来的请求。
  • 一个处理请求和返回响应的处理器。

处理器是一个简单的函数,接受任意个数的参数并且返回任意类型的结果。

用来匹配的参数包括静态路径、动态路径、路径参数、表单、查询参数、特定的请求格式和 请求体数据。Rocket 利用属性(类似其它语言的装饰器一样),使得路由声明变得加单。路由声明就是给处理器方法添加注解并且有一组参数用来匹配。一个完整的路由声明是像这样的:

#[get("/world")]              // <- route attribute
fn world() -> &'static str {  // <- request handler
      "Hello, world!"
}

这个声明了world路由用来匹配静态路径"/world"GET请求。"world"路由比较简单,不过当构建复杂的应用个的时候,额外的路由参数是必须的。请求 一节里面讲解了构建路由的所有情况。

挂载

在Rocket 能够分发请求到一个路由之前,路由需要先完成挂载。 挂载路由,类似给路由一个命名空间。用 Rocket实例的mount方法来挂载一个路由。Rocket实例通常使用rocket::ignite()静态方法来创建。

mount方法需要:

  • 一个包含一系列路由的命名空间的路径。
  • 一组对应路由的处理器!和生成Rocket应用代码的宏。

例如,挂载之前声明的world路由,我们可以这样写:

rocket::ignite().mount("/hello", routes![world]);

这块代码通过 ignite 函数创建了一个新的Rocket实例,并且将 world路由挂载到了“/hello” 路径下面。
其结果就是,GET请求 “/hello/world”路径就会访问world函数。

命名空间

当一个路由是在root之外的其它模块里声明的,你会在挂载的时候会得到一个异常:

mod other {
    #[get("/world")]
    pub fn world() -> &'static str {
        "Hello, world!"
    }
}

use other::world;

fn main() {
  // error[E0425]: cannot find value `static_rocket_route_info_for_world` in this scope
  rocket::ignite().mount("/hello", routes![world]);
}

这个错误出现是因为 宏 routes! 在生成Rocket代码的时候隐式地将 route的名称 转换为了当前解构里的名称。解决方法是在写路由名称的时候加上模块的名字:

rocket::ignite().mount("/hello", routes![other::world]);

运行

现在Rocket已经有了路由,你可以用launch方法来启动Rocket接受请求。launch用来方法启动服务等待请求。当请求到达时,Rocket 会找到匹配的路由,并将请求分发到该路由的处理器。

通常情况下我们在main方法里调用launch方法。现在我们已经完成了Hello, world!程序,看起来像这样:

#![feature(plugin)]
#![plugin(rocket_codegen)]

extern crate rocket;

#[get("/world")]
fn world() -> &'static str {
    "Hello, world!"
}

fn main() {
    rocket::ignite().mount("/hello", routes![world]).launch();
}

注意到我们添加了#![feature(plugin)]#![plugin(rocket_codegen)]这两行,是告诉Rust我们使用了Rocket的代码生成插件。同样我们将通过extern crate rocketrocket crate(箱)引入了我们的命名空间。最后,我们在main函数里调用了launch 方法。

运行这个程序,控制台会显示内容:

🔧  Configured for development.
    => address: localhost
    => port: 8000
    => log: normal
    => workers: [logical cores * 2]
    => secret key: generated
    => limits: forms = 32KiB
    => tls: disabled
🛰  Mounting '/hello':
    => GET /hello/world
🚀  Rocket has launched from http://localhost:8000

我们访问 localhost:8000/hello/world,就会看到Hello, world, 正好是我们预期的。

GitHub上有这个例子一个完整版的crate(箱),只要cargo run 就能运行。 你可以在 GitHub examples directory 中找到更多的例子,涵盖了所有Rocket的特性。

Rocket系列 >>

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,456评论 5 477
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,370评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,337评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,583评论 1 273
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,596评论 5 365
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,572评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,936评论 3 395
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,595评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,850评论 1 297
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,601评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,685评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,371评论 4 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,951评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,934评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,167评论 1 259
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 43,636评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,411评论 2 342

推荐阅读更多精彩内容