SQLx是一個(gè)Rust語(yǔ)言的異步SQL執(zhí)行庫(kù),它支持多種數(shù)據(jù)庫(kù),包括MySQL、PostgreSQL、SQLite等。本教程將以MySQL數(shù)據(jù)庫(kù)為例,介紹SQLx在Rust語(yǔ)言中的基礎(chǔ)用法和進(jìn)階用法。
基礎(chǔ)用法
要使用SQLx,需要在Cargo.toml
文件中添加以下依賴:
[dependencies]
sqlx = { version = "0.6", features = ["mysql", "runtime-tokio-rustls"] }
tokio = { version = "1", features = ["full"] }
連接數(shù)據(jù)庫(kù)
在使用SQLx之前,需要先連接數(shù)據(jù)庫(kù)。SQLx提供了兩種方式連接MySQL數(shù)據(jù)庫(kù):使用URL連接和使用配置文件連接。
URL連接
使用URL連接時(shí),需要在代碼中指定連接字符串,例如:
use sqlx::mysql::MySqlPoolOptions;
#[tokio::main]
async fn main() - > Result< (), sqlx::Error > {
let pool = MySqlPoolOptions::new()
.max_connections(5)
.connect("mysql://username:password@hostname:port/database")
.await?;
// ...
Ok(())
}
其中,username
和password
是數(shù)據(jù)庫(kù)用戶名和密碼,hostname
是數(shù)據(jù)庫(kù)主機(jī)名,port
是數(shù)據(jù)庫(kù)端口號(hào),database
是要連接的數(shù)據(jù)庫(kù)名。
配置文件連接
使用配置文件連接時(shí),需要在項(xiàng)目根目錄下創(chuàng)建一個(gè)名為.env
的文件,并在其中指定連接信息,例如:
DATABASE_URL=mysql://username:password@hostname:port/database
然后在代碼中使用dotenv
庫(kù)加載.env
文件,并使用sqlx::MySqlPool::connect_dotenv()
方法連接數(shù)據(jù)庫(kù),例如:
use sqlx::mysql::MySqlPoolOptions;
#[tokio::main]
async fn main() - > Result< (), sqlx::Error > {
dotenv::dotenv().ok();
let pool = MySqlPoolOptions::new()
.max_connections(5)
.connect_dotenv()
.await?;
// ...
Ok(())
}
查詢數(shù)據(jù)
連接成功后,就可以使用SQLx執(zhí)行SQL查詢語(yǔ)句了。SQLx提供了兩種方式執(zhí)行SQL查詢語(yǔ)句:使用query()
方法和使用query_as()
方法。
使用query()方法
使用query()
方法執(zhí)行SQL查詢語(yǔ)句時(shí),需要手動(dòng)指定返回結(jié)果的類型,例如:
use sqlx::{MySqlPool, Row};
#[derive(Debug)]
struct User {
id: i32,
name: String,
}
#[tokio::main]
async fn main() - > Result< (), sqlx::Error > {
let pool = MySqlPool::connect("mysql://username:password@hostname:port/database").await?;
let mut conn = pool.acquire().await?;
let mut rows = sqlx::query("SELECT id, name FROM users")
.map(|row: sqlx::mysql::MySqlRow| {
User {
id: row.get(0),
name: row.get(1),
}
})
.fetch_all(&mut conn)
.await?;
for row in rows.iter() {
println!("{:?}", row);
}
Ok(())
}
使用query_as()方法
使用query_as()
方法執(zhí)行SQL查詢語(yǔ)句時(shí),可以自動(dòng)將返回結(jié)果轉(zhuǎn)換為指定類型的結(jié)構(gòu)體,例如:
use sqlx::{MySqlPool, FromRow};
#[derive(Debug, FromRow)]
struct User {
id: i32,
name: String,
}
#[tokio::main]
async fn main() - > Result< (), sqlx::Error > {
let pool = MySqlPool::connect("mysql://username:password@hostname:port/database").await?;
let mut conn = pool.acquire().await?;
let mut rows = sqlx::query_as::< _, User >("SELECT id, name FROM users")
.fetch_all(&mut conn)
.await?;
for row in rows.iter() {
println!("{:?}", row);
}
Ok(())
}
插入數(shù)據(jù)
使用SQLx插入數(shù)據(jù)時(shí),可以使用execute()
方法或execute_with()
方法。
使用execute()方法
使用execute()
方法插入數(shù)據(jù)時(shí),需要手動(dòng)指定插入的數(shù)據(jù),例如:
use sqlx::{MySqlPool, Row};
#[derive(Debug)]
struct User {
name: String,
}
#[tokio::main]
async fn main() - > Result< (), sqlx::Error > {
let pool = MySqlPool::connect("mysql://username:password@hostname:port/database").await?;
let mut conn = pool.acquire().await?;
let user = User {
name: "John".to_string(),
};
let result = sqlx::query("INSERT INTO users (name) VALUES (?)")
.bind(user.name)
.execute(&mut conn)
.await?;
println!("{:?}", result);
Ok(())
}
使用execute_with()方法
使用execute_with()
方法插入數(shù)據(jù)時(shí),可以使用結(jié)構(gòu)體自動(dòng)映射的特性,例如:
use sqlx::{MySqlPool, FromRow};
#[derive(Debug, FromRow)]
struct User {
name: String,
}
#[tokio::main]
async fn main() - > Result< (), sqlx::Error > {
let pool = MySqlPool::connect("mysql://username:password@hostname:port/database").await?;
let mut conn = pool.acquire().await?;
let user = User {
name: "John".to_string(),
};
let result = sqlx::query_with::< _, User >("INSERT INTO users (name) VALUES (?)", user)
.execute(&mut conn)
.await?;
println!("{:?}", result);
Ok(())
}
更新數(shù)據(jù)
使用SQLx更新數(shù)據(jù)時(shí),可以使用execute()
方法或execute_with()
方法。
使用execute()方法
使用execute()
方法更新數(shù)據(jù)時(shí),需要手動(dòng)指定更新的條件和更新的數(shù)據(jù),例如:
use sqlx::{MySqlPool, Row};
#[derive(Debug)]
struct User {
id: i32,
name: String,
}
#[tokio::main]
async fn main() - > Result< (), sqlx::Error > {
let pool = MySqlPool::connect("mysql://username:password@hostname:port/database").await?;
let mut conn = pool.acquire().await?;
let user = User {
id: 1,
name: "John".to_string(),
};
let result = sqlx::query("UPDATE users SET name = ? WHERE id = ?")
.bind(user.name)
.bind(user.id)
.execute(&mut conn)
.await?;
println!("{:?}", result);
Ok(())
}
使用execute_with()方法
使用execute_with()
方法更新數(shù)據(jù)時(shí),可以使用結(jié)構(gòu)體自動(dòng)映射的特性,例如:
use sqlx::{MySqlPool, FromRow};
#[derive(Debug, FromRow)]
struct User {
id: i32,
name: String,
}
#[tokio::main]
async fn main() - > Result< (), sqlx::Error > {
let pool = MySqlPool::connect("mysql://username:password@hostname:port/database").await?;
let mut conn = pool.acquire().await?;
let user = User {
id: 1,
name: "John".to_string(),
};
let result = sqlx::query_with::< _, User >("UPDATE users SET name = :name WHERE id = :id", user)
.execute(&mut conn)
.await?;
println!("{:?}", result);
Ok(())
}
刪除數(shù)據(jù)
使用SQLx刪除數(shù)據(jù)時(shí),可以使用execute()
方法或execute_with()
方法。
使用execute()方法
使用execute()
方法刪除數(shù)據(jù)時(shí),需要手動(dòng)指定刪除的條件,例如:
use sqlx::{MySqlPool, Row};
#[tokio::main]
async fn main() - > Result< (), sqlx::Error > {
let pool = MySqlPool::connect("mysql://username:password@hostname:port/database").await?;
let mut conn = pool.acquire().await?;
let result = sqlx::query("DELETE FROM users WHERE id = ?")
.bind(1)
.execute(&mut conn)
.await?;
println!("{:?}", result);
Ok(())
}
使用execute_with()方法
使用execute_with()
方法刪除數(shù)據(jù)時(shí),可以使用結(jié)構(gòu)體自動(dòng)映射的特性,例如:
use sqlx::{MySqlPool, FromRow};
#[derive(Debug, FromRow)]
struct User {
id: i32,
}
#[tokio::main]
async fn main() - > Result< (), sqlx::Error > {
let pool = MySqlPool::connect("mysql://username:password@hostname:port/database").await?;
let mut conn = pool.acquire().await?;
let user = User {
id: 1,
};
let result = sqlx::query_with::< _, User >("DELETE FROM users WHERE id = :id", user)
.execute(&mut conn)
.await?;
println!("{:?}", result);
Ok(())
}
進(jìn)階用法
事務(wù)
使用SQLx執(zhí)行事務(wù)時(shí),可以使用begin()
方法開始事務(wù),使用commit()
方法提交事務(wù),使用rollback()
方法回滾事務(wù)。
use sqlx::{MySqlPool, Transaction};
#[derive(Debug)]
struct User {
name: String,
}
#[tokio::main]
async fn main() - > Result< (), sqlx::Error > {
let pool = MySqlPool::connect("mysql://username:password@hostname:port/database").await?;
let mut conn = pool.acquire().await?;
let mut tx = conn.begin().await?;
let user = User {
name: "John".to_string(),
};
let result = sqlx::query("INSERT INTO users (name) VALUES (?)")
.bind(user.name)
.execute(&mut tx)
.await?;
println!("{:?}", result);
tx.commit().await?;
Ok(())
}
連接池
使用SQLx連接池時(shí),可以使用PoolOptions::new()
方法創(chuàng)建連接池,并使用acquire()
方法獲取連接。
use sqlx::{MySqlPool, PoolOptions};
#[tokio::main]
async fn main() - > Result< (), sqlx::Error > {
let pool = MySqlPool::connect("mysql://username:password@hostname:port/database").await?;
let mut conn = pool.acquire().await?;
let pool = MySqlPool::builder()
.max_size(5)
.build("mysql://username:password@hostname:port/database")
.await?;
let mut conn = pool.acquire().await?;
// ...
Ok(())
}
總結(jié)
本教程介紹了SQLx在Rust語(yǔ)言中的基礎(chǔ)用法和進(jìn)階用法,包括連接數(shù)據(jù)庫(kù)、查詢數(shù)據(jù)、插入數(shù)據(jù)、更新數(shù)據(jù)、刪除數(shù)據(jù)、事務(wù)和連接池等。SQLx是一個(gè)簡(jiǎn)單易用的異步SQL執(zhí)行庫(kù),可以幫助Rust開發(fā)者快速地與多種數(shù)據(jù)庫(kù)進(jìn)行交互。
-
SQL
+關(guān)注
關(guān)注
1文章
753瀏覽量
44032 -
數(shù)據(jù)庫(kù)
+關(guān)注
關(guān)注
7文章
3752瀏覽量
64233 -
文件
+關(guān)注
關(guān)注
1文章
561瀏覽量
24671 -
代碼
+關(guān)注
關(guān)注
30文章
4722瀏覽量
68231 -
rust語(yǔ)言
+關(guān)注
關(guān)注
0文章
57瀏覽量
3001 -
SQLx
+關(guān)注
關(guān)注
0文章
2瀏覽量
34
發(fā)布評(píng)論請(qǐng)先 登錄
相關(guān)推薦
評(píng)論