Improve API
This commit is contained in:
parent
6203d967eb
commit
486a081509
@ -6,11 +6,20 @@ CREATE TABLE `cake` (
|
|||||||
PRIMARY KEY (`id`)
|
PRIMARY KEY (`id`)
|
||||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
|
||||||
|
|
||||||
|
INSERT INTO `cake` (`id`, `name`) VALUES
|
||||||
|
(1, 'New York Cheese'),
|
||||||
|
(2, 'Chocolate Fudge');
|
||||||
|
|
||||||
DROP TABLE IF EXISTS `fruit`;
|
DROP TABLE IF EXISTS `fruit`;
|
||||||
|
|
||||||
CREATE TABLE `fruit` (
|
CREATE TABLE `fruit` (
|
||||||
`id` int NOT NULL AUTO_INCREMENT,
|
`id` int NOT NULL AUTO_INCREMENT,
|
||||||
`name` varchar(255) DEFAULT NULL,
|
`name` varchar(255) DEFAULT NULL,
|
||||||
`cake_id` int,
|
`cake_id` int DEFAULT NULL,
|
||||||
PRIMARY KEY (`id`)
|
PRIMARY KEY (`id`)
|
||||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
|
||||||
|
|
||||||
|
INSERT INTO `fruit` (`id`, `name`, `cake_id`) VALUES
|
||||||
|
(1, 'Blueberry', 1),
|
||||||
|
(2, 'Rasberry', 1),
|
||||||
|
(3, 'Strawberry', 2);
|
@ -117,7 +117,6 @@ impl IdenStatic for Column {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// TODO: implement with derive macro
|
// TODO: implement with derive macro
|
||||||
impl Iden for PrimaryKey {
|
impl Iden for PrimaryKey {
|
||||||
fn unquoted(&self, s: &mut dyn std::fmt::Write) {
|
fn unquoted(&self, s: &mut dyn std::fmt::Write) {
|
||||||
|
@ -15,7 +15,7 @@ async fn main() {
|
|||||||
println!("{:?}", db);
|
println!("{:?}", db);
|
||||||
println!();
|
println!();
|
||||||
|
|
||||||
println!("find all");
|
print!("find all: ");
|
||||||
|
|
||||||
let cakes = cake::Entity::find().all(&db).await.unwrap();
|
let cakes = cake::Entity::find().all(&db).await.unwrap();
|
||||||
|
|
||||||
@ -25,15 +25,23 @@ async fn main() {
|
|||||||
println!();
|
println!();
|
||||||
}
|
}
|
||||||
|
|
||||||
println!("find one by primary key");
|
let fruits = fruit::Entity::find().all(&db).await.unwrap();
|
||||||
|
|
||||||
let cheese = cake::Entity::find_one(&db, 1).await.unwrap();
|
println!();
|
||||||
|
for cc in fruits.iter() {
|
||||||
|
println!("{:?}", cc);
|
||||||
|
println!();
|
||||||
|
}
|
||||||
|
|
||||||
|
print!("find one by primary key: ");
|
||||||
|
|
||||||
|
let cheese = cake::Entity::find_by(1).one(&db).await.unwrap();
|
||||||
|
|
||||||
println!();
|
println!();
|
||||||
println!("{:?}", cheese);
|
println!("{:?}", cheese);
|
||||||
println!();
|
println!();
|
||||||
|
|
||||||
println!("find models belongs to");
|
print!("find models belong to: ");
|
||||||
|
|
||||||
let fruits = cheese.find_fruit().all(&db).await.unwrap();
|
let fruits = cheese.find_fruit().all(&db).await.unwrap();
|
||||||
|
|
||||||
|
@ -4,8 +4,9 @@ impl<E: 'static> Select<E>
|
|||||||
where
|
where
|
||||||
E: EntityTrait,
|
E: EntityTrait,
|
||||||
{
|
{
|
||||||
pub async fn one(self, db: &Database) -> Result<E::Model, QueryErr> {
|
pub async fn one(mut self, db: &Database) -> Result<E::Model, QueryErr> {
|
||||||
let builder = db.get_query_builder_backend();
|
let builder = db.get_query_builder_backend();
|
||||||
|
self.query().limit(1);
|
||||||
let row = db.get_connection().query_one(self.build(builder)).await?;
|
let row = db.get_connection().query_one(self.build(builder)).await?;
|
||||||
Ok(<E as EntityTrait>::Model::from_query_result(row)?)
|
Ok(<E as EntityTrait>::Model::from_query_result(row)?)
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,5 @@
|
|||||||
use crate::{
|
use crate::{
|
||||||
ColumnTrait, Connection, Database, ModelTrait, PrimaryKeyTrait, QueryErr, RelationBuilder,
|
ColumnTrait, ModelTrait, PrimaryKeyTrait, RelationBuilder, RelationTrait, RelationType, Select,
|
||||||
RelationTrait, RelationType, Select,
|
|
||||||
};
|
};
|
||||||
use async_trait::async_trait;
|
use async_trait::async_trait;
|
||||||
use sea_query::{Expr, Iden, IntoIden, Value};
|
use sea_query::{Expr, Iden, IntoIden, Value};
|
||||||
@ -41,13 +40,6 @@ pub trait EntityTrait: EntityName {
|
|||||||
RelationBuilder::new(RelationType::HasMany, Self::default(), entity)
|
RelationBuilder::new(RelationType::HasMany, Self::default(), entity)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn belongs_to<E>(entity: E) -> RelationBuilder
|
|
||||||
where
|
|
||||||
E: IntoIden,
|
|
||||||
{
|
|
||||||
RelationBuilder::new(RelationType::BelongsTo, Self::default(), entity)
|
|
||||||
}
|
|
||||||
|
|
||||||
/// ```
|
/// ```
|
||||||
/// use sea_orm::{ColumnTrait, EntityTrait, tests_cfg::cake, sea_query::MysqlQueryBuilder};
|
/// use sea_orm::{ColumnTrait, EntityTrait, tests_cfg::cake, sea_query::MysqlQueryBuilder};
|
||||||
///
|
///
|
||||||
@ -62,12 +54,21 @@ pub trait EntityTrait: EntityName {
|
|||||||
Select::<Self>::new()
|
Select::<Self>::new()
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn find_one<V>(db: &Database, v: V) -> Result<Self::Model, QueryErr>
|
/// Find a model by primary key
|
||||||
|
/// ```
|
||||||
|
/// use sea_orm::{ColumnTrait, EntityTrait, tests_cfg::cake, sea_query::MysqlQueryBuilder};
|
||||||
|
///
|
||||||
|
/// assert_eq!(
|
||||||
|
/// cake::Entity::find_by(11)
|
||||||
|
/// .build(MysqlQueryBuilder)
|
||||||
|
/// .to_string(),
|
||||||
|
/// "SELECT `cake`.`id`, `cake`.`name` FROM `cake` WHERE `cake`.`id` = 11"
|
||||||
|
/// );
|
||||||
|
/// ```
|
||||||
|
fn find_by<V>(v: V) -> Select<Self>
|
||||||
where
|
where
|
||||||
V: Into<Value> + Send,
|
V: Into<Value>,
|
||||||
{
|
{
|
||||||
let builder = db.get_query_builder_backend();
|
|
||||||
let stmt = {
|
|
||||||
let mut select = Self::find();
|
let mut select = Self::find();
|
||||||
if let Some(key) = Self::PrimaryKey::iter().next() {
|
if let Some(key) = Self::PrimaryKey::iter().next() {
|
||||||
// TODO: supporting composite primary key
|
// TODO: supporting composite primary key
|
||||||
@ -75,9 +76,6 @@ pub trait EntityTrait: EntityName {
|
|||||||
} else {
|
} else {
|
||||||
panic!("undefined primary key");
|
panic!("undefined primary key");
|
||||||
}
|
}
|
||||||
select.build(builder)
|
select
|
||||||
};
|
|
||||||
let row = db.get_connection().query_one(stmt).await?;
|
|
||||||
Ok(Self::Model::from_query_result(row)?)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -31,6 +31,17 @@ pub trait ColumnTrait: IdenStatic {
|
|||||||
bind_oper!(lt);
|
bind_oper!(lt);
|
||||||
bind_oper!(lte);
|
bind_oper!(lte);
|
||||||
|
|
||||||
|
/// ```
|
||||||
|
/// use sea_orm::{ColumnTrait, EntityTrait, tests_cfg::cake, sea_query::MysqlQueryBuilder};
|
||||||
|
///
|
||||||
|
/// assert_eq!(
|
||||||
|
/// cake::Entity::find()
|
||||||
|
/// .filter(cake::Column::Id.between(2,3))
|
||||||
|
/// .build(MysqlQueryBuilder)
|
||||||
|
/// .to_string(),
|
||||||
|
/// "SELECT `cake`.`id`, `cake`.`name` FROM `cake` WHERE `cake`.`id` BETWEEN 2 AND 3"
|
||||||
|
/// );
|
||||||
|
/// ```
|
||||||
fn between<V>(&self, a: V, b: V) -> SimpleExpr
|
fn between<V>(&self, a: V, b: V) -> SimpleExpr
|
||||||
where
|
where
|
||||||
V: Into<Value>,
|
V: Into<Value>,
|
||||||
@ -38,6 +49,17 @@ pub trait ColumnTrait: IdenStatic {
|
|||||||
Expr::tbl(self.as_iden(), *self).between(a, b)
|
Expr::tbl(self.as_iden(), *self).between(a, b)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// ```
|
||||||
|
/// use sea_orm::{ColumnTrait, EntityTrait, tests_cfg::cake, sea_query::MysqlQueryBuilder};
|
||||||
|
///
|
||||||
|
/// assert_eq!(
|
||||||
|
/// cake::Entity::find()
|
||||||
|
/// .filter(cake::Column::Id.not_between(2,3))
|
||||||
|
/// .build(MysqlQueryBuilder)
|
||||||
|
/// .to_string(),
|
||||||
|
/// "SELECT `cake`.`id`, `cake`.`name` FROM `cake` WHERE `cake`.`id` NOT BETWEEN 2 AND 3"
|
||||||
|
/// );
|
||||||
|
/// ```
|
||||||
fn not_between<V>(&self, a: V, b: V) -> SimpleExpr
|
fn not_between<V>(&self, a: V, b: V) -> SimpleExpr
|
||||||
where
|
where
|
||||||
V: Into<Value>,
|
V: Into<Value>,
|
||||||
|
@ -7,7 +7,6 @@ use std::rc::Rc;
|
|||||||
pub enum RelationType {
|
pub enum RelationType {
|
||||||
HasOne,
|
HasOne,
|
||||||
HasMany,
|
HasMany,
|
||||||
BelongsTo,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub trait RelationTrait: Debug + 'static {
|
pub trait RelationTrait: Debug + 'static {
|
||||||
|
@ -8,7 +8,7 @@ pub use sea_query::JoinType;
|
|||||||
use sea_query::{Expr, Iden, IntoIden, Order, QueryBuilder, SelectStatement, SimpleExpr};
|
use sea_query::{Expr, Iden, IntoIden, Order, QueryBuilder, SelectStatement, SimpleExpr};
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Clone, Debug)]
|
||||||
pub struct Select<E: 'static>
|
pub struct Select<E: 'static>
|
||||||
where
|
where
|
||||||
E: EntityTrait,
|
E: EntityTrait,
|
||||||
|
@ -117,7 +117,6 @@ impl IdenStatic for Column {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// TODO: implement with derive macro
|
// TODO: implement with derive macro
|
||||||
impl Iden for PrimaryKey {
|
impl Iden for PrimaryKey {
|
||||||
fn unquoted(&self, s: &mut dyn std::fmt::Write) {
|
fn unquoted(&self, s: &mut dyn std::fmt::Write) {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user