所有文章 > 如何集成API > Rust + MongoDB + Actix Web:构建 CRUD REST API 教程
Rust + MongoDB + Actix Web:构建 CRUD REST API 教程

Rust + MongoDB + Actix Web:构建 CRUD REST API 教程

在本教程中,我们将使用 RustMongoDBActix Web 创建一个支持 创建、读取、更新和删除(CRUD) 操作的 REST API。以 PersonHobby 两个模型为例,这两个模型存在一对多关系:在 MongoDB 中,Hobby 集合通过引用 Person 的 ID 来实现关联。

最终,我们将实现如下 REST API 端点:

  • POST /api/v1/persons:创建新 Person
  • GET /api/v1/persons:获取所有 Person
  • GET /api/v1/persons/:id:根据 ID 获取指定 Person
  • PUT /api/v1/persons/:id:更新指定 Person
  • DELETE /api/v1/persons/:id:删除指定 Person
  • POST /api/v1/hobbies:创建新 Hobby
  • GET /api/v1/hobbies:获取所有 Hobby
  • GET /api/v1/hobbies/:id:根据 ID 获取指定 Hobby
  • PUT /api/v1/hobbies/:id:更新指定 Hobby
  • DELETE /api/v1/hobbies/:id:删除指定 Hobby

一. 准备工作

在开始之前,请确保已安装:

  1. Rust 和 Cargo CLI
  2. MongoDB
  3. Visual Studio Code (VSCode)(推荐)

二. 设置 MongoDB

1. 安装 MongoDB(macOS 示例)

brew tap mongodb/brew
brew install mongodb-community
brew services start mongodb/brew/mongodb-community
brew services list

2. 创建数据库用户

use admin
db.createUser({
  user: "rustadmin",
  pwd: "Adm1n_pwd",
  roles: ["readWrite", "dbAdmin"]
})

3. 启用安全认证

编辑 MongoDB 配置文件:

security:
  authorization: "enabled"

保存后重启服务:

brew services restart mongodb/brew/mongodb-community

三. 设置 Rust 开发环境

1. 安装 Rust

curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh
rustc -V
cargo -V

2. 配置 VSCode

安装扩展:

  • Rust
  • Rust Analyzer
  • Prettier – Code formatter

四. 创建 Rust REST-API 项目

1. 初始化项目

cargo new rust_mongo_rest
cd rust_mongo_rest

项目结构:

rust_mongo_rest/
├── Cargo.toml
└── src/
    └── main.rs

2. 添加依赖项

Cargo.toml 中添加:

[dependencies]
actix-web = "4"
mongodb = "3.1.0"
serde = { version = "1.0", features = ["derive"] }
serde_json = "1.0"
dotenv = "0.15"
futures = "0.3"
tokio = { version = "1", features = ["full"] }
chrono = { version = "*", features = ["serde"] }

运行:

cargo build

五. 连接 MongoDB

1. 创建 .env

DB_USERNAME=rustadmin
DB_PASSWORD=Adm1n_pwd
DB_URL=mongodb://localhost:27017
DB_NAME=rust_mongo
DB_AUTH_SOURCE=admin

2. 实现数据库连接 (src/db.rs)

use mongodb::{options::{ClientOptions, Credential}, Client};
use std::env;

pub async fn get_mongo_client() -> Client {
    dotenv::dotenv().ok();
    let username = env::var("DB_USERNAME").expect("DB_USERNAME must be set");
    let password = env::var("DB_PASSWORD").expect("DB_PASSWORD must be set");
    let host = env::var("DB_URL").unwrap_or_else(|_| "localhost".to_string());
    let auth_source = env::var("DB_AUTH_SOURCE").unwrap_or_else(|_| "admin".to_string());

    let credential = Credential::builder()
        .username(Some(username))
        .password(Some(password))
        .source(Some(auth_source))
        .build();

    let client_options = ClientOptions::builder()
        .hosts(vec![host])
        .credential(Some(credential))
        .build();

    Client::with_options(client_options).unwrap()
}

六. 创建模型

1. 文件结构

mkdir src/models
touch src/models/person.rs
touch src/models/hobby.rs
touch src/models/mod.rs

2. 定义模型

person.rs

use mongodb::bson::oid::ObjectId;
use serde::{Deserialize, Serialize};
use chrono::Utc;

#[derive(Debug, Serialize, Deserialize)]
pub struct Person {
    #[serde(rename = "_id", skip_serializing_if = "Option::is_none")]
    pub id: Option<ObjectId>,
    pub name: String,
    pub email: String,
    pub created_at: chrono::DateTime<Utc>,
}

hobby.rs

use mongodb::bson::oid::ObjectId;
use serde::{Deserialize, Serialize};

#[derive(Debug, Serialize, Deserialize)]
pub struct Hobby {
    #[serde(rename = "_id", skip_serializing_if = "Option::is_none")]
    pub id: Option<ObjectId>,
    pub hobby_name: String,
    pub description: String,
    pub person: Option<ObjectId>,
}

mod.rs

pub mod person;
pub mod hobby;

七. 创建处理器和路由

1. 处理器文件夹

mkdir src/handlers
touch src/handlers/person.rs
touch src/handlers/hobby.rs
touch src/handlers/mod.rs

person.rshobby.rs 中实现 CRUD 逻辑。

2. 路由配置 (src/routes.rs)

use actix_web::web;
use crate::handlers::{person, hobby};

pub fn configure_routes(cfg: &mut web::ServiceConfig) {
    cfg.service(
        web::scope("/api/v1")
            .route("/persons", web::post().to(person::create_person))
            .route("/persons", web::get().to(person::get_persons))
            .route("/persons/{id}", web::get().to(person::get_person_by_id))
            .route("/persons/{id}", web::put().to(person::update_person_by_id))
            .route("/persons/{id}", web::delete().to(person::delete_person_by_id))
            .route("/hobbies", web::post().to(hobby::create_hobby))
            .route("/hobbies", web::get().to(hobby::get_hobbies))
            .route("/hobbies/{id}", web::get().to(hobby::get_hobby_by_id))
            .route("/hobbies/{id}", web::put().to(hobby::update_hobby_by_id))
            .route("/hobbies/{id}", web::delete().to(hobby::delete_hobby_by_id)),
    );
}

八. 启动应用程序 (main.rs)

use actix_web::{App, HttpServer};
use crate::db::get_mongo_client;
mod db;
mod models;
mod handlers;
mod routes;

#[actix_web::main]
async fn main() -> std::io::Result<()> {
    let client = get_mongo_client().await;

    HttpServer::new(move || {
        App::new()
            .app_data(client.clone())
            .configure(routes::configure_routes)
    })
    .bind("127.0.0.1:8080")?
    .run()
    .await
}

九. 测试 REST API

启动应用:

cargo run

示例:创建 Person

curl -X POST http://127.0.0.1:8080/api/v1/persons \
-H "Content-Type: application/json" \
-d '{"name": "Graydon Hoare", "email": "graydon@example.com"}'

通过本教程,你已成功使用 Rust、MongoDB 和 Actix Web 构建了一个完整的 CRUD REST API,支持一对多模型关联,可作为后续业务扩展的基础。

原文链接: https://www.djamware.com/post/674bc4ad5127914b1112d912/rust-and-mongodb-tutorial-create-crud-rest-api

#你可能也喜欢这些API文章!

我们有何不同?

API服务商零注册

多API并行试用

数据驱动选型,提升决策效率

查看全部API→
🔥

热门场景实测,选对API

#AI文本生成大模型API

对比大模型API的内容创意新颖性、情感共鸣力、商业转化潜力

25个渠道
一键对比试用API 限时免费

#AI深度推理大模型API

对比大模型API的逻辑推理准确性、分析深度、可视化建议合理性

10个渠道
一键对比试用API 限时免费