前置准备
添加依赖
sqlx = { version = "", features = ["runtime-tokio", "mysql"] }
- sqlx启用mysql功能
schema.sql文件修改(初始化数据脚本)
-- 创建用户表
CREATE TABLE IF NOT EXISTS users (
id INT AUTO_INCREMENT PRIMARY KEY,
name VARCHAR) NOT NULL,
email VARCHAR) NOT NULL
);
-- 清空表
TRUNCATE TABLE users;
-- 插入测试数据
INSERT INTO users (name, email) VALUES
('张三', 'zhangsan@example.com'),
('李四', 'lisi@example.com'),
('王五', 'wangwu@example.com'),
('赵六', 'zhaoliu@example.com');
.env文件调整
DATABASE_URL=mysql://root:root@localhost:/rust_http
user_handler.rs文件调整
- 函数签名中State泛型改为MySqlPool
async fn get_users(
State(db): State, // 从 State 中提取数据库连接池
Query(query): Query, // 从 Query 中提取查询参数
) -> Result>, (StatusCode, String)> { ... }
- 修改sql语句
sqlx::query_as!(
User,
"SELECT id, name, email FROM users WHERE name LIKE ?",
pattern
)
使用sqlx::query_as!宏来执行一个参数化的 SQL 查询,在编译时检查 SQL 查询字段是否与目标的 User 类型字段匹配,确保返回的列和 User 结构定义的一致性,并且将查询返回的记录自动映射为 User 类型的结构体实例,pattern是与 ? 占位符对应的参数,从而避免sql注入问题。
main.rs文件调整
- 创建Mysql连接池
let db = MySqlPool::connect(&std::env::var("DATABASE_URL")?).await?;
.await绑定一个异步操作;?运算符用于优雅地处理错误,如果连接失败会返回错误
user_routes.rs文件调整
- 函数签名返回类型改为MySqlPool
pub fn user_routes() -> Router {...}
总结
sqlx通过sqlx::query_as!宏提供了统一的查询,使得更改数据源非常方便,所要修改的只是查询语句以及连接池部分。