diff --git a/crates/client/src/lib.rs b/crates/client/src/lib.rs index 826ac26..73712f2 100644 --- a/crates/client/src/lib.rs +++ b/crates/client/src/lib.rs @@ -10,9 +10,11 @@ use anyhow::{anyhow, Result}; use reqwest::Url; use auth::AuthClient; +use post::PostClient; pub struct Client { pub auth: AuthClient, + pub post: PostClient, } impl Client { @@ -24,6 +26,7 @@ impl Client { Ok(Self { auth: AuthClient::new(domain.clone()), + post: PostClient::new(domain.clone()), }) } } diff --git a/crates/client/src/modules/mod.rs b/crates/client/src/modules/mod.rs index 2e5a125..20beca7 100644 --- a/crates/client/src/modules/mod.rs +++ b/crates/client/src/modules/mod.rs @@ -1,3 +1,4 @@ pub mod auth; +pub mod post; pub(crate) type DateTime = chrono::DateTime; diff --git a/crates/client/src/modules/post/mod.rs b/crates/client/src/modules/post/mod.rs new file mode 100644 index 0000000..07d090b --- /dev/null +++ b/crates/client/src/modules/post/mod.rs @@ -0,0 +1,29 @@ +pub mod posts; + +use anyhow::Result; +use pxid::Pxid; +use reqwest::{Client, Url}; + +pub struct PostClient { + client: Client, + domain: Url, +} + +impl PostClient { + pub fn new(domain: Url) -> Self { + Self { + domain, + client: Client::new(), + } + } + + pub async fn posts( + &self, + after: Option, + before: Option, + first: Option, + last: Option, + ) -> Result { + posts::posts(self, after, before, first, last).await + } +} diff --git a/crates/client/src/modules/post/posts/Posts.gql b/crates/client/src/modules/post/posts/Posts.gql new file mode 100644 index 0000000..3c0ed32 --- /dev/null +++ b/crates/client/src/modules/post/posts/Posts.gql @@ -0,0 +1,34 @@ +query Posts($after: Pxid, $before: Pxid, $first: Int, $last: Int) { + posts(after: $after, before: $before, first: $first, last: $last) { + edges { + node { + id + title + content + createdAt + updatedAt + author { + id + name + surname + username + email + createdAt + updatedAt + avatar { + id + url + } + } + } + cursor + } + totalCount + pageInfo { + hasNextPage + hasPreviousPage + startCursor + endCursor + } + } +} diff --git a/crates/client/src/modules/post/posts/mod.rs b/crates/client/src/modules/post/posts/mod.rs new file mode 100644 index 0000000..e0b45ca --- /dev/null +++ b/crates/client/src/modules/post/posts/mod.rs @@ -0,0 +1,55 @@ +use anyhow::{anyhow, bail, Result}; +use graphql_client::reqwest::post_graphql; +use graphql_client::GraphQLQuery; +use pxid::Pxid; + +use posts::{PostsPostsEdges, PostsPostsPageInfo, Variables}; + +use crate::{DateTime, GRAPHQL_PATH}; + +use super::PostClient; + +#[derive(GraphQLQuery)] +#[graphql( + response_derives = "Clone,Debug,Deserialize", + schema_path = "schema.json", + query_path = "src/modules/post/posts/Posts.gql" +)] +pub struct Posts { + pub edges: Vec, + pub total_count: i64, + pub page_info: PostsPostsPageInfo, +} + +pub async fn posts( + public_client: &PostClient, + after: Option, + before: Option, + first: Option, + last: Option, +) -> Result { + let url = public_client.domain.join(GRAPHQL_PATH)?; + + let res = post_graphql::( + &public_client.client, + url, + Variables { + after, + before, + first, + last, + }, + ) + .await + .map_err(|err| anyhow!("Failed to make request. {err}"))?; + + if let Some(ref data) = res.data { + return Ok(Posts { + edges: data.posts.edges.to_owned(), + total_count: data.posts.total_count, + page_info: data.posts.page_info.to_owned(), + }); + } + + bail!("Failed to get posts. err = {:#?}", res.errors.unwrap()) +} diff --git a/crates/web/src/components/auth/login.rs b/crates/web/src/components/auth/login.rs index c102a5c..8c976f1 100644 --- a/crates/web/src/components/auth/login.rs +++ b/crates/web/src/components/auth/login.rs @@ -5,7 +5,7 @@ use leptos::{ use townhall_client::Client; -use crate::components::button::{Button, ButtonType, ButtonVariant}; +use crate::components::button::{Button, ButtonType}; use crate::components::text_field::{TextField, TextFieldType}; #[component] diff --git a/crates/web/src/components/auth/register.rs b/crates/web/src/components/auth/register.rs index 689f46b..a73a663 100644 --- a/crates/web/src/components/auth/register.rs +++ b/crates/web/src/components/auth/register.rs @@ -8,7 +8,7 @@ use leptos::{ use townhall_client::Client; use townhall_types::user::Email; -use crate::components::button::{Button, ButtonType, ButtonVariant}; +use crate::components::button::{Button, ButtonType}; use crate::components::text_field::{TextField, TextFieldType}; #[component] diff --git a/crates/web/src/components/button.rs b/crates/web/src/components/button.rs index 632c423..173b564 100644 --- a/crates/web/src/components/button.rs +++ b/crates/web/src/components/button.rs @@ -39,7 +39,7 @@ pub fn Button( #[prop(optional, into)] full_width: MaybeProp, #[prop(optional, into)] variant: MaybeProp, #[prop(optional)] children: Option, - #[prop(optional, into)] on_click: MaybeProp () + 'static>>, + #[prop(optional, into)] on_click: MaybeProp>, #[prop(optional, into)] r#type: ButtonType, ) -> impl IntoView { let custom_classes = class.get();