Actix-Web 中定义路由的5种方法

一、开始

本文主要讲解,如何初始化一个 actix-web 项目,以及各种定义路由方式。

二、初始化一个项目

首先需要有 rust 的运行环境,使用 Rust Cargo 初始一个项目:

sh 复制代码
cargo new <your_project_name>
  • 添加依赖
toml 复制代码
[dependencies]  
actix-web = "4"
  • 一个最简单的应用
rs 复制代码
use actix_web::{get, App, HttpResponse, HttpServer, Responder};

#[get("/")]
async fn hello() -> impl Responder {
    HttpResponse::Ok().body("Hello world!")
}

#[actix_web::main]
async fn main() -> std::io::Result<()> {
    HttpServer::new(|| {
        App::new()
            .service(hello)
    })
    .bind(("127.0.0.1", 8080))?
    .run()
    .await
}

分析:从 actix_web 包中,导入了 HTTP 相关的内容,HttpServer 用于初始化 HTTP 服务,App 用于初始化 应用服务,HttpServer 实例化的过程汇总需要一个闭包函数,在闭包函数中实例化 App, 并且在 App 中定义好路由。接下来就可以启动此服务了。

  • 运行服务
sh 复制代码
cargo run

三、定义路由的各种方法

3.1)route 函数单独定义

rs 复制代码
use actix_web::{App, web, HttpResponse, HttpServer, Responder};

async fn hello() -> impl Responder {
    HttpResponse::Ok().body("Hello world!")
}

#[actix_web::main]
async fn main() -> std::io::Result<()> {
    HttpServer::new(|| {
        App::new()
            .route("/", web::get().to(hello))
    })
    .bind(("127.0.0.1", 8080))?
    .run()
    .await
}

此处使用 route 函数进行定义,需要 web 配合指定,方法是 get 已及它的处理函数是 hello

3.2)service 函数单独定义

  • 以 post 方法为例
rs 复制代码
use actix_web::{post, App, HttpResponse, HttpServer, Responder};

#[post("/")]
async fn echo(req_body: String) -> impl Responder {
    HttpResponse::Ok().body(req_body)
}

#[actix_web::main]
async fn main() -> std::io::Result<()> {
    HttpServer::new(|| App::new().service(echo))
        .bind(("127.0.0.1", 8080))?
        .run()
        .await
}

service 与 route 不同的是, service 是通过 rust 注解的形式获取定义请求的方式和路由参数。

3.3)resource 函数成组定义

rs 复制代码
pub fn resource<T: IntoPatterns>(path: T) -> Resource {
    Resource::new(path)
}
  • 定义资源群 resource,以下示例是:
rs 复制代码
use actix_web::{web, App, HttpResponse, HttpServer, Responder};

async fn users_list() -> impl Responder {
    HttpResponse::Ok().body("List of users")
}

async fn user_info(path: web::Path<(String,)>) -> impl Responder {
    let username = &path.0;
    HttpResponse::Ok().body(format!("User info for: {}", username))
}

async fn create_user() -> impl Responder {
    HttpResponse::Created().body("User created successfully")
}

#[actix_web::main]
async fn main() -> std::io::Result<()> {
    HttpServer::new(|| {
        App::new()
            .service(
                web::resource("/users")
                    .route(web::get().to(users_list)) // GET /users
                    .route(web::post().to(create_user)), // POST /users
            )
            .service(
                web::resource("/users/{username}")
                    .route(web::get().to(user_info)), // GET /users/{username}
            )
    })
    .bind("127.0.0.1:8080")?
    .run()
    .await
}

resource 定义一个路由资源,此时就可以使用 route 方法处理不同方法的请求。在此实例中,使用 service 方法 与 web::resource 进行配合可以成组使用。service 单独使用的案例之前已经说过了。

3.4)configure 函数自定定义配置路由

rs 复制代码
use actix_web::{web, App, HttpResponse, HttpServer};

fn config(cfg: &mut web::ServiceConfig) {
    cfg.service(
        web::resource("/app")
            .route(web::get().to(|| async { HttpResponse::Ok().body("app") }))
            .route(web::head().to(HttpResponse::MethodNotAllowed)),
    );
}

#[actix_web::main]
async fn main() -> std::io::Result<()> {
    HttpServer::new(|| {
        App::new()
            .configure(config)
    })
    .bind(("127.0.0.1", 8080))?
    .run()
    .await
}

configure 方法能够定义 config 函数,在 config 函数中,获取 cfg 对象,cfg 中存在 service, 相当于一个子服务。在模块拆分的时候非常有用。

3.5) scope 函数定义作用域

rs 复制代码
use actix_web::{web, App, HttpServer, Responder};

async fn index() -> impl Responder {
    "Hello world!"
}

#[actix_web::main]
async fn main() -> std::io::Result<()> {
    HttpServer::new(|| {
        App::new().service(
            // prefixes all resources and routes attached to it...
            web::scope("/app")
                // ...so this handles requests for `GET /app/index.html`
                .route("/index", web::get().to(index)),
        )
    })
    .bind(("127.0.0.1", 8080))?
    .run()
    .await
}

web::scope 的用法与 web::resource 用法类似,后者针对于当前资源使用不同的方式处理,前者可以定义子路由,并指定不同的方法。scope 更加的灵活

四、小结

本文主要关注 actix-web 中定义路由的多种方式。从一个简单的示例开始,到route 函数的单独订立,然后是 service 函数定义,resource 函数定义统一方法的多重处理方式,configure 函数可以可以拆分函数配置,scope 使用作用域配置与 resource 类似,但是更加灵活。

相关推荐
吃杠碰小鸡31 分钟前
lodash常用函数
前端·javascript
emoji11111141 分钟前
前端对页面数据进行缓存
开发语言·前端·javascript
泰伦闲鱼44 分钟前
nestjs:GET REQUEST 缓存问题
服务器·前端·缓存·node.js·nestjs
m0_748250031 小时前
Web 第一次作业 初探html 使用VSCode工具开发
前端·html
一个处女座的程序猿O(∩_∩)O1 小时前
vue3 如何使用 mounted
前端·javascript·vue.js
m0_748235951 小时前
web复习(三)
前端
搬码后生仔1 小时前
asp.net core webapi项目中 在生产环境中 进不去swagger
chrome·后端·asp.net
凡人的AI工具箱1 小时前
每天40分玩转Django:Django国际化
数据库·人工智能·后端·python·django·sqlite
AiFlutter1 小时前
Flutter-底部分享弹窗(showModalBottomSheet)
java·前端·flutter
麦兜*1 小时前
轮播图带详情插件、uniApp插件
前端·javascript·uni-app·vue