mirror of
https://github.com/Lumither/nocturne.git
synced 2026-10-17 10:26:21 +00:00
fix(blog::api) fix pagination for GET posts
This commit is contained in:
3 files changed
+51
-25
No files matched your search
@@ -0,0 +1,20 @@
|
|||||||
|
WITH filtered_posts AS
|
||||||
|
(SELECT p.id, p.date_created
|
||||||
|
FROM posts p
|
||||||
|
WHERE $1::text[] IS NULL
|
||||||
|
OR (
|
||||||
|
CASE
|
||||||
|
WHEN $4 THEN (SELECT COUNT(DISTINCT t.name)
|
||||||
|
FROM post_tag pt
|
||||||
|
JOIN tags t ON pt.tag = t.id
|
||||||
|
WHERE pt.post = p.id
|
||||||
|
AND t.name = ANY ($1::text[])) = cardinality($1)
|
||||||
|
ELSE EXISTS (SELECT 1
|
||||||
|
FROM post_tag pt
|
||||||
|
JOIN tags t ON pt.tag = t.id
|
||||||
|
WHERE pt.post = p.id
|
||||||
|
AND t.name = ANY ($1::text[]))
|
||||||
|
END
|
||||||
|
))
|
||||||
|
SELECT COUNT(*) AS total_count
|
||||||
|
FROM filtered_posts;
|
||||||
@@ -106,20 +106,25 @@ struct UuidRow {
|
|||||||
id: Uuid,
|
id: Uuid,
|
||||||
}
|
}
|
||||||
|
|
||||||
const GET_POST_WITH_BRIEF_MODEL: &str = include_str!("get_post_with_brief_model.sql");
|
const I32_PLACEHOLDER: i32 = 0;
|
||||||
|
|
||||||
|
const COUNT_TAG_FILTERED_POSTS: &str = include_str!("count_tag_filtered_posts.sql");
|
||||||
const SELECT_POST_WITH_TAG_FILTER_PAGINATED: &str =
|
const SELECT_POST_WITH_TAG_FILTER_PAGINATED: &str =
|
||||||
include_str!("select_post_with_tag_filter_paginated.sql");
|
include_str!("select_post_with_tag_filter_paginated.sql");
|
||||||
|
const GET_POST_WITH_BRIEF_MODEL: &str = include_str!("get_post_with_brief_model.sql");
|
||||||
|
|
||||||
pub async fn handler(
|
pub async fn handler(
|
||||||
State(db): State<PgPool>,
|
State(db): State<PgPool>,
|
||||||
Query(search_params): Query<SearchParams>,
|
Query(search_params): Query<SearchParams>,
|
||||||
) -> impl IntoResponse {
|
) -> impl IntoResponse {
|
||||||
dbg!(&search_params.tags);
|
|
||||||
dbg!(&search_params.match_all);
|
|
||||||
|
|
||||||
let page = search_params.page.unwrap_or(1);
|
let page = search_params.page.unwrap_or(1);
|
||||||
let page_size = search_params.page_size.unwrap_or(PAGE_SIZE);
|
let page_size = search_params.page_size.unwrap_or(PAGE_SIZE);
|
||||||
let page_count = match sqlx::query_scalar::<_, i64>("SELECT COUNT(*) FROM posts")
|
|
||||||
|
let page_count = match sqlx::query_scalar::<_, i64>(COUNT_TAG_FILTERED_POSTS)
|
||||||
|
.bind(&search_params.tags)
|
||||||
|
.bind(I32_PLACEHOLDER) // not used, but help sqlx/psql hit cache
|
||||||
|
.bind(I32_PLACEHOLDER)
|
||||||
|
.bind(search_params.match_all)
|
||||||
.fetch_one(&db)
|
.fetch_one(&db)
|
||||||
.await
|
.await
|
||||||
{
|
{
|
||||||
|
|||||||
+21
-20
@@ -1,21 +1,22 @@
|
|||||||
SELECT p.id
|
WITH filtered_posts AS
|
||||||
FROM posts p
|
(SELECT p.id, p.date_created
|
||||||
WHERE $1::text[] IS NULL
|
FROM posts p
|
||||||
OR (
|
WHERE $1::text[] IS NULL
|
||||||
CASE
|
OR (
|
||||||
WHEN $4 THEN (SELECT COUNT(DISTINCT t.name)
|
CASE
|
||||||
FROM post_tag pt
|
WHEN $4 THEN (SELECT COUNT(DISTINCT t.name)
|
||||||
JOIN tags t ON pt.tag = t.id
|
FROM post_tag pt
|
||||||
WHERE pt.post = p.id
|
JOIN tags t ON pt.tag = t.id
|
||||||
AND t.name = ANY ($1::text[]))
|
WHERE pt.post = p.id
|
||||||
= cardinality($1)
|
AND t.name = ANY ($1::text[])) = cardinality($1)
|
||||||
ELSE
|
ELSE EXISTS (SELECT 1
|
||||||
EXISTS (SELECT 1
|
FROM post_tag pt
|
||||||
FROM post_tag pt
|
JOIN tags t ON pt.tag = t.id
|
||||||
JOIN tags t ON pt.tag = t.id
|
WHERE pt.post = p.id
|
||||||
WHERE pt.post = p.id
|
AND t.name = ANY ($1::text[]))
|
||||||
AND t.name = ANY ($1::text[]))
|
END
|
||||||
END
|
))
|
||||||
)
|
SELECT id
|
||||||
ORDER BY p.date_created DESC
|
FROM filtered_posts
|
||||||
|
ORDER BY date_created DESC
|
||||||
LIMIT $2 OFFSET $3;
|
LIMIT $2 OFFSET $3;
|
||||||
Reference in new issue
Block a user