OrangeGuidanceTomestone/server/src/web/get_location.rs

52 lines
1.7 KiB
Rust
Raw Normal View History

2022-09-03 10:35:15 +00:00
use std::sync::Arc;
use anyhow::Context;
use warp::{Filter, Rejection, Reply};
use warp::filters::BoxedFilter;
use crate::message::RetrievedMessage;
use crate::State;
use crate::web::AnyhowRejection;
pub fn get_location(state: Arc<State>) -> BoxedFilter<(impl Reply, )> {
warp::get()
.and(warp::path("messages"))
.and(warp::path::param())
.and(warp::path::end())
2022-09-04 03:50:30 +00:00
.and(super::get_id(Arc::clone(&state)))
.and_then(move |location: u32, id: i64| logic(Arc::clone(&state), id, location))
2022-09-03 10:35:15 +00:00
.boxed()
}
2022-09-04 03:50:30 +00:00
async fn logic(state: Arc<State>, id: i64, location: u32) -> Result<impl Reply, Rejection> {
// TODO: when we're not just returning all results, make sure own messages are always present
2022-09-04 07:12:51 +00:00
let location = location as i64;
2022-09-03 10:35:15 +00:00
let messages = sqlx::query_as!(
RetrievedMessage,
// language=sqlite
r#"
select m.id,
m.x,
m.y,
m.z,
2022-09-04 21:04:44 +00:00
m.yaw,
2022-09-03 10:35:15 +00:00
m.message,
coalesce(sum(v.vote between 0 and 1), 0) as positive_votes,
2022-09-04 07:12:51 +00:00
coalesce(sum(v.vote between -1 and 0), 0) as negative_votes,
v2.vote as user_vote
2022-09-03 10:35:15 +00:00
from messages m
left join votes v on m.id = v.message
2022-09-04 07:12:51 +00:00
left join votes v2 on m.id = v2.message and v2.user = ?
2022-09-03 10:35:15 +00:00
where m.territory = ?
group by m.id"#,
id,
2022-09-04 07:12:51 +00:00
location,
2022-09-03 10:35:15 +00:00
)
.fetch_all(&state.db)
.await
.context("could not get messages from database")
.map_err(AnyhowRejection)
.map_err(warp::reject::custom)?;
Ok(warp::reply::json(&messages))
}