only show top 10 participants + total amount
This commit is contained in:
@@ -1,40 +1,102 @@
|
||||
use crate::{Backend, model::client::Client};
|
||||
use crate::{model::client::Client, Backend};
|
||||
|
||||
pub(crate) struct Rank {
|
||||
pub(crate) rank: i64,
|
||||
pub(crate) client: Client,
|
||||
pub(crate) amount: i64,
|
||||
pub(crate) show_dots_above: bool,
|
||||
}
|
||||
|
||||
impl Backend {
|
||||
pub(crate) async fn highscore(&self) -> Vec<Rank> {
|
||||
pub(crate) async fn amount_participants(&self) -> i64 {
|
||||
match self {
|
||||
Backend::Sqlite(db) => {
|
||||
let row = sqlx::query!("SELECT COUNT(*) as count FROM client")
|
||||
.fetch_one(db)
|
||||
.await
|
||||
.unwrap();
|
||||
|
||||
row.count
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) async fn highscore(&self, client: &Client) -> Vec<Rank> {
|
||||
match self {
|
||||
Backend::Sqlite(db) => {
|
||||
let rows = sqlx::query!(
|
||||
"SELECT
|
||||
DENSE_RANK() OVER (ORDER BY COUNT(s.client_uuid) DESC) as rank,
|
||||
c.name,
|
||||
c.uuid,
|
||||
COUNT(s.client_uuid) as amount
|
||||
FROM client c
|
||||
LEFT JOIN sightings s ON c.uuid = s.client_uuid
|
||||
GROUP BY c.uuid, c.name
|
||||
ORDER BY amount DESC"
|
||||
"WITH ranked_clients AS (
|
||||
SELECT
|
||||
DENSE_RANK() OVER (ORDER BY COUNT(s.client_uuid) DESC) as rank,
|
||||
c.name,
|
||||
c.uuid,
|
||||
COUNT(s.client_uuid) as amount
|
||||
FROM client c
|
||||
LEFT JOIN sightings s ON c.uuid = s.client_uuid
|
||||
GROUP BY c.uuid, c.name
|
||||
)
|
||||
SELECT rank, name, uuid, amount
|
||||
FROM ranked_clients
|
||||
WHERE rank <= (
|
||||
SELECT rank
|
||||
FROM ranked_clients
|
||||
ORDER BY rank
|
||||
LIMIT 1 OFFSET 9
|
||||
)
|
||||
ORDER BY rank, name"
|
||||
)
|
||||
.fetch_all(db)
|
||||
.await
|
||||
.unwrap_or_default();
|
||||
|
||||
rows.into_iter()
|
||||
let mut ret: Vec<Rank> = rows
|
||||
.into_iter()
|
||||
.map(|row| Rank {
|
||||
rank: row.rank.unwrap(),
|
||||
client: Client {
|
||||
uuid: row.uuid.unwrap(),
|
||||
name: row.name,
|
||||
},
|
||||
amount: row.amount.unwrap(),
|
||||
show_dots_above: false,
|
||||
})
|
||||
.collect();
|
||||
|
||||
let user_is_in_top = ret.iter().find(|x| &x.client == client).is_some();
|
||||
if !user_is_in_top {
|
||||
let row = sqlx::query!(
|
||||
"WITH ranked_clients AS (
|
||||
SELECT
|
||||
DENSE_RANK() OVER (ORDER BY COUNT(s.client_uuid) DESC) as rank,
|
||||
c.name,
|
||||
c.uuid,
|
||||
COUNT(s.client_uuid) as amount
|
||||
FROM client c
|
||||
LEFT JOIN sightings s ON c.uuid = s.client_uuid
|
||||
GROUP BY c.uuid, c.name
|
||||
)
|
||||
SELECT rank, name, uuid, amount
|
||||
FROM ranked_clients
|
||||
WHERE uuid = ?
|
||||
ORDER BY rank, name",
|
||||
client.uuid
|
||||
)
|
||||
.fetch_one(db)
|
||||
.await
|
||||
.unwrap();
|
||||
|
||||
ret.push(Rank {
|
||||
rank: row.rank,
|
||||
client: Client {
|
||||
uuid: row.uuid,
|
||||
name: row.name,
|
||||
},
|
||||
amount: row.amount,
|
||||
show_dots_above: true,
|
||||
})
|
||||
.collect()
|
||||
}
|
||||
|
||||
ret
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user