From ab50826d31e49318aafca27795a5c8911bd260cb Mon Sep 17 00:00:00 2001 From: ecco257 Date: Fri, 4 Oct 2024 17:44:10 -0400 Subject: [PATCH 01/16] Update formatting of profile login buttons and display --- src/components/personal.rs | 6 +++--- style/personal.scss | 31 ++++++++++++++----------------- 2 files changed, 17 insertions(+), 20 deletions(-) diff --git a/src/components/personal.rs b/src/components/personal.rs index 889a780..48ee134 100644 --- a/src/components/personal.rs +++ b/src/components/personal.rs @@ -33,10 +33,10 @@ pub fn Profile() -> impl IntoView { #[component] pub fn DropDownNotLoggedIn() -> impl IntoView { view! { - } } +#[component] +pub fn DropDownLoggedIn(user_signal: RwSignal, logged_in: RwSignal) -> impl IntoView { + + let logout = move |_| { + spawn_local(async move { + let result = logout().await; + if let Err(err) = result { + log!("Error logging out: {:?}", err); + } else { + log!("Logged out successfully"); + user_signal.update(|value| *value = User::default()); + logged_in.set(false); + } + }); + }; + + view! { + + } +} diff --git a/src/models.rs b/src/models.rs index b96c8d2..59baec3 100644 --- a/src/models.rs +++ b/src/models.rs @@ -25,7 +25,7 @@ cfg_if! { #[cfg_attr(feature = "ssr", derive(Queryable, Selectable, Insertable))] #[cfg_attr(feature = "ssr", diesel(table_name = crate::schema::users))] #[cfg_attr(feature = "ssr", diesel(check_for_backend(diesel::pg::Pg)))] -#[derive(Serialize, Deserialize, Clone, Debug)] +#[derive(Serialize, Deserialize, Clone, Debug, Default)] pub struct User { /// A unique id for the user #[cfg_attr(feature = "ssr", diesel(deserialize_as = i32))] diff --git a/src/users.rs b/src/users.rs index 2d61c69..387dfcd 100644 --- a/src/users.rs +++ b/src/users.rs @@ -117,7 +117,7 @@ pub async fn validate_user(credentials: UserCredentials) -> Result, /// Get a user from the database by username or email /// Returns a Result with the user if found, None if not found, or an error if there was a problem -#[server(endpoint = "get_user")] +#[server(endpoint = "find_user")] pub async fn get_user(username_or_email: String) -> Result, ServerFnError> { let mut user = find_user(username_or_email).await?; From 071dcad0cc873cd8b08b885ad9ae900205c65f56 Mon Sep 17 00:00:00 2001 From: ecco257 Date: Tue, 15 Oct 2024 17:17:44 -0400 Subject: [PATCH 03/16] Convert borders and margins to rem from px in profile --- style/personal.scss | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/style/personal.scss b/style/personal.scss index 7b142d4..08c6e93 100644 --- a/style/personal.scss +++ b/style/personal.scss @@ -4,7 +4,7 @@ width: 16rem; background: #1c1c1c; height: 100vh; - margin: 2px; + margin: 0.2rem; border-radius: 0.5rem; .profile-container { @@ -12,7 +12,7 @@ border-radius: 0.4rem; margin: 0.2rem; min-height: 6rem; - border: 2px solid rgba(89, 89, 89, 0.199); + border: 0.2rem solid rgba(89, 89, 89, 0.199); padding: 0.5rem; .profile-icon { @@ -43,7 +43,7 @@ width: 10rem; z-index: 1; background-color: #1c1c1c; - border: 2px solid rgba(89, 89, 89, 0.199); + border: 0.2rem solid rgba(89, 89, 89, 0.199); .dropdown-logged { display: flex; @@ -55,15 +55,15 @@ font-size: 1.2rem; } .auth-button { - margin-top: 0.5rem; - padding: 0.5rem; - border-radius: 0.5rem; - background-color: #1c1c1c; - border: 2px solid rgba(89, 89, 89, 0.199); - color: white; - cursor: pointer; - transition: all 0.3s; - margin-bottom: 0.5rem; + margin-top: 0.5rem; + padding: 0.5rem; + border-radius: 0.5rem; + background-color: #1c1c1c; + border: 0.2rem solid rgba(89, 89, 89, 0.199); + color: white; + cursor: pointer; + transition: all 0.3s; + margin-bottom: 0.5rem; } } } From f78066d7a8aab2186466d0a6e2d744777f92f411 Mon Sep 17 00:00:00 2001 From: ecco257 Date: Tue, 15 Oct 2024 17:18:41 -0400 Subject: [PATCH 04/16] Display username in profile when logged in --- src/components/personal.rs | 10 ++++++---- style/personal.scss | 11 +++++++++++ 2 files changed, 17 insertions(+), 4 deletions(-) diff --git a/src/components/personal.rs b/src/components/personal.rs index a7c4141..7ee63dd 100644 --- a/src/components/personal.rs +++ b/src/components/personal.rs @@ -18,17 +18,16 @@ pub fn Personal() -> impl IntoView { pub fn Profile() -> impl IntoView { let (dropdown_open, set_dropdown_open) = create_signal(false); let logged_in = create_rw_signal(false); - let user_signal = create_rw_signal(User::default()); - - let open_dropdown = move |_| { spawn_local(async move { let user = get_user().await; if let Ok(user) = user { logged_in.set(true); - user_signal.update(|value| *value = user); + user_signal.update(|value| { + *value = user; + }); } else { logged_in.set(false); } @@ -82,6 +81,9 @@ pub fn DropDownLoggedIn(user_signal: RwSignal, logged_in: RwSignal) view! { } diff --git a/style/personal.scss b/style/personal.scss index 08c6e93..de02199 100644 --- a/style/personal.scss +++ b/style/personal.scss @@ -54,6 +54,17 @@ h1 { font-size: 1.2rem; } + .profile-info { + display: flex; + width: 100%; + justify-content: center; + border-top: 0.2rem solid rgba(89, 89, 89, 0.199); + border-bottom: 0.2rem solid rgba(89, 89, 89, 0.199); + h1 { + font-size: 1rem; + margin-top: 0.5rem; + } + } .auth-button { margin-top: 0.5rem; padding: 0.5rem; From f104a14f98b73cc582d7c4b9c7169d74c5da5922 Mon Sep 17 00:00:00 2001 From: ecco257 Date: Tue, 15 Oct 2024 17:26:30 -0400 Subject: [PATCH 05/16] Remove derive Default for User and make user signal Option type instead --- src/components/personal.rs | 17 ++++++++++++----- src/models.rs | 2 +- 2 files changed, 13 insertions(+), 6 deletions(-) diff --git a/src/components/personal.rs b/src/components/personal.rs index 7ee63dd..bce2901 100644 --- a/src/components/personal.rs +++ b/src/components/personal.rs @@ -18,7 +18,8 @@ pub fn Personal() -> impl IntoView { pub fn Profile() -> impl IntoView { let (dropdown_open, set_dropdown_open) = create_signal(false); let logged_in = create_rw_signal(false); - let user_signal = create_rw_signal(User::default()); + // user signal is an option because the user may not be logged in + let user_signal = create_rw_signal(None); let open_dropdown = move |_| { spawn_local(async move { @@ -26,7 +27,7 @@ pub fn Profile() -> impl IntoView { if let Ok(user) = user { logged_in.set(true); user_signal.update(|value| { - *value = user; + *value = Some(user); }); } else { logged_in.set(false); @@ -63,7 +64,7 @@ pub fn DropDownNotLoggedIn() -> impl IntoView { } } #[component] -pub fn DropDownLoggedIn(user_signal: RwSignal, logged_in: RwSignal) -> impl IntoView { +pub fn DropDownLoggedIn(user_signal: RwSignal>, logged_in: RwSignal) -> impl IntoView { let logout = move |_| { spawn_local(async move { @@ -72,7 +73,7 @@ pub fn DropDownLoggedIn(user_signal: RwSignal, logged_in: RwSignal) log!("Error logging out: {:?}", err); } else { log!("Logged out successfully"); - user_signal.update(|value| *value = User::default()); + user_signal.update(|value| *value = None); logged_in.set(false); } }); @@ -82,7 +83,13 @@ pub fn DropDownLoggedIn(user_signal: RwSignal, logged_in: RwSignal) diff --git a/src/models.rs b/src/models.rs index 59baec3..b96c8d2 100644 --- a/src/models.rs +++ b/src/models.rs @@ -25,7 +25,7 @@ cfg_if! { #[cfg_attr(feature = "ssr", derive(Queryable, Selectable, Insertable))] #[cfg_attr(feature = "ssr", diesel(table_name = crate::schema::users))] #[cfg_attr(feature = "ssr", diesel(check_for_backend(diesel::pg::Pg)))] -#[derive(Serialize, Deserialize, Clone, Debug, Default)] +#[derive(Serialize, Deserialize, Clone, Debug)] pub struct User { /// A unique id for the user #[cfg_attr(feature = "ssr", diesel(deserialize_as = i32))] From 2be665c549411dafe118f5d92ea88e776e3b4b63 Mon Sep 17 00:00:00 2001 From: ecco257 Date: Fri, 18 Oct 2024 19:26:10 -0400 Subject: [PATCH 06/16] Track logged in status and user as local resource instead of signal --- src/components/personal.rs | 34 ++++++---------------------------- 1 file changed, 6 insertions(+), 28 deletions(-) diff --git a/src/components/personal.rs b/src/components/personal.rs index bce2901..9a68575 100644 --- a/src/components/personal.rs +++ b/src/components/personal.rs @@ -17,23 +17,11 @@ pub fn Personal() -> impl IntoView { #[component] pub fn Profile() -> impl IntoView { let (dropdown_open, set_dropdown_open) = create_signal(false); - let logged_in = create_rw_signal(false); - // user signal is an option because the user may not be logged in - let user_signal = create_rw_signal(None); + let user = create_local_resource(move || dropdown_open.get(), |_| async move { get_user().await }); + let logged_in = create_local_resource(move || dropdown_open.get(), |_| async move { get_user().await.is_ok() }); let open_dropdown = move |_| { - spawn_local(async move { - let user = get_user().await; - if let Ok(user) = user { - logged_in.set(true); - user_signal.update(|value| { - *value = Some(user); - }); - } else { - logged_in.set(false); - } - set_dropdown_open.update(|value| *value = !*value); - }); + set_dropdown_open.update(|value| *value = !*value); }; view! { @@ -43,11 +31,11 @@ pub fn Profile() -> impl IntoView { @@ -64,7 +52,7 @@ pub fn DropDownNotLoggedIn() -> impl IntoView { } } #[component] -pub fn DropDownLoggedIn(user_signal: RwSignal>, logged_in: RwSignal) -> impl IntoView { +pub fn DropDownLoggedIn(logged_in: Resource) -> impl IntoView { let logout = move |_| { spawn_local(async move { @@ -73,7 +61,6 @@ pub fn DropDownLoggedIn(user_signal: RwSignal>, logged_in: RwSignal log!("Error logging out: {:?}", err); } else { log!("Logged out successfully"); - user_signal.update(|value| *value = None); logged_in.set(false); } }); @@ -82,15 +69,6 @@ pub fn DropDownLoggedIn(user_signal: RwSignal>, logged_in: RwSignal view! { } From c2ebd8307f35d432ffed4f27397e30876c67560e Mon Sep 17 00:00:00 2001 From: ecco257 Date: Fri, 18 Oct 2024 19:30:45 -0400 Subject: [PATCH 07/16] Display user profile picture when logged in instead of generic profile icon --- src/components/personal.rs | 19 +++++++++++++++++-- 1 file changed, 17 insertions(+), 2 deletions(-) diff --git a/src/components/personal.rs b/src/components/personal.rs index 9a68575..6cb8090 100644 --- a/src/components/personal.rs +++ b/src/components/personal.rs @@ -3,7 +3,6 @@ use leptos::*; use leptos_icons::*; use crate::auth::get_user; use crate::auth::logout; -use crate::models::User; #[component] pub fn Personal() -> impl IntoView { @@ -24,10 +23,26 @@ pub fn Profile() -> impl IntoView { set_dropdown_open.update(|value| *value = !*value); }; + let user_profile_picture = move || { + user.get().map(|user| { + if let Ok(user) = user { + return format!("/assets/images/profile/{}.webp", user.id.unwrap()); + } else { + return "".to_string(); + } + }) + }; + view! {
- + + }> + +