Diesel 是目前 Rust 生态中最流行的 ORM 框架,但是对数据库函数的支持并不是很完善,如果在需要调用一些自定义函数或者一些框架暂时未支持的函数时,在 Diesel 中就需要通过 define_sql_function! 宏来进行扩展了 。
下面以json_contains和json_extract为例,演示在 Diesel 中使用 define_sql_function! 宏来做自定义函数支持。
先对函数进行定义。
use diesel::define_sql_function;
use diesel::sql_types::*;
define_sql_function! {
fn json_contains(target: Nullable<Json>, candidate: Text) -> Bool;
}
define_sql_function! {
fn json_extract(json: Nullable<Json>, path: Text) -> Nullable<Json>;
}
``
接着就是在需要的地方进行调用,可以看下面这段 rust 代码,先从 whites json 中取出 users 列表,然后判断是否包含 user_id。
```rust
apps::user_id.eq(user_id).or(functions::json_contains(
functions::json_extract(apps::whites, "$.users"),
format!(r#"["{}"]"#, user_id),
))
apps.whites 结构如下:
{"users": ["123"], "communities": []}
假设 user_id 为 123,上面 rust 代码对应的 sql 条件就是:
user_id = 123 or json_contains(json_extract(whites, "$.users"), "[123]")
其它在 Diesel 中还没有支持的函数都可以采用这种方法定义。