from_query_result_opt, FIXME: unit test will fail

This commit is contained in:
Billy Chan 2021-06-24 18:56:07 +08:00 committed by Chris Tsang
parent 19c0b0c35d
commit a072b1f2f3
2 changed files with 42 additions and 31 deletions

View File

@ -14,4 +14,11 @@ pub trait FromQueryResult {
fn from_query_result(res: &QueryResult, pre: &str) -> Result<Self, TypeErr>
where
Self: Sized;
fn from_query_result_opt(res: &QueryResult, pre: &str) -> Result<Option<Self>, TypeErr>
where
Self: Sized,
{
Ok(Self::from_query_result(res, pre).ok())
}
}

View File

@ -52,12 +52,12 @@ where
M: FromQueryResult + Sized,
N: FromQueryResult + Sized,
{
type Item = (M, N);
type Item = (M, Option<N>);
fn from_raw_query_result(res: QueryResult) -> Result<Self::Item, TypeErr> {
Ok((
M::from_query_result(&res, combine::SELECT_A)?,
N::from_query_result(&res, combine::SELECT_B)?,
N::from_query_result_opt(&res, combine::SELECT_B)?,
))
}
}
@ -125,37 +125,10 @@ where
}
}
fn parse_query_result(rows: Vec<(E::Model, F::Model)>) -> Vec<(E::Model, Vec<F::Model>)> {
let mut acc = Vec::new();
for (l_model, r_model) in rows {
if acc.is_empty() {
acc.push((l_model, vec![r_model]));
continue;
}
let (last_l, last_r) = acc.last_mut().unwrap();
let mut l_equal = true;
for pk_col in <E::PrimaryKey as Iterable>::iter() {
let col = pk_col.into_column();
let curr_val = l_model.get(col);
let last_val = last_l.get(col);
if !curr_val.eq(&last_val) {
l_equal = false;
break;
}
}
if l_equal {
last_r.push(r_model);
} else {
acc.push((l_model, vec![r_model]));
}
}
acc
}
pub async fn one(
self,
db: &DatabaseConnection,
) -> Result<Option<(E::Model, F::Model)>, QueryErr> {
) -> Result<Option<(E::Model, Option<F::Model>)>, QueryErr> {
self.into_model::<E::Model, F::Model>().one(db).await
}
@ -164,7 +137,7 @@ where
db: &DatabaseConnection,
) -> Result<Vec<(E::Model, Vec<F::Model>)>, QueryErr> {
let rows = self.into_model::<E::Model, F::Model>().all(db).await?;
Ok(Self::parse_query_result(rows))
Ok(parse_query_result::<E, _>(rows))
}
}
@ -202,3 +175,34 @@ where
}
}
}
fn parse_query_result<L, R>(rows: Vec<(L::Model, Option<R>)>) -> Vec<(L::Model, Vec<R>)>
where
L: EntityTrait,
{
let mut acc: Vec<(L::Model, Vec<R>)> = Vec::new();
for (l, r) in rows {
if let Some((last_l, last_r)) = acc.last_mut() {
let mut same_l = true;
for pk_col in <L::PrimaryKey as Iterable>::iter() {
let col = pk_col.into_column();
let val = l.get(col);
let last_val = last_l.get(col);
if !val.eq(&last_val) {
same_l = false;
break;
}
}
if same_l && r.is_some() {
last_r.push(r.unwrap());
continue;
}
}
if r.is_some() {
acc.push((l, vec![r.unwrap()]));
} else {
acc.push((l, vec![]));
}
}
acc
}