Skip to content

Commit

Permalink
Merge branch 'user_data_updates'
Browse files Browse the repository at this point in the history
  • Loading branch information
g-pooja-03 committed Nov 18, 2024
2 parents 5a29225 + 99a1f97 commit 0de00a1
Show file tree
Hide file tree
Showing 22 changed files with 626 additions and 200 deletions.
9 changes: 4 additions & 5 deletions client/src/components/fakestackoverflow.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import AccountInfo from './main/profile/accountInfo';
import TagsInfo from './main/profile/tags';
import CommunityInfo from './main/profile/community';
import ChooseTagsPage from './login/newUser/chooseTagsPage/index';
import ChooseCommunityPage from './login/newUser/chooseCommunityPage';
import CommunityHomePage from './main/homePage/community';
import PostLoginCommunity from './login/newUser/chooseCommunityPage';
import ChatPage from './main/chat';
Expand Down Expand Up @@ -52,10 +53,8 @@ const FakeStackOverflow = ({ socket }: { socket: FakeSOSocket | null }) => {
<Route path='/existing' element={<Login />} />
<Route path='/new' element={<CreateUser />} />
<Route path='/new/tagselection' element={<ChooseTagsPage />} />
<Route
path='/new/tagselection/communityselection'
element={<PostLoginCommunity userId={user?.username || ''} />}
/>
<Route path='/new/tagselection/communityselection' element={<ChooseCommunityPage />} />

{/* Protected Routes */}
{
<Route
Expand All @@ -75,7 +74,7 @@ const FakeStackOverflow = ({ socket }: { socket: FakeSOSocket | null }) => {
<Route path='profile' element={<ProfilePage />}>
<Route path='account' element={<AccountInfo />} />
<Route path='tags' element={<TagsInfo />} />
<Route path='community' element={<CommunityInfo userId={user?.username || ''} />} />
{/* <Route path='community' element={<CommunityInfo/>} /> */}
</Route>
</Route>
}
Expand Down
86 changes: 53 additions & 33 deletions client/src/components/login/newUser/chooseCommunityPage/index.css
Original file line number Diff line number Diff line change
Expand Up @@ -3,75 +3,95 @@
flex-direction: column;
align-items: center;
justify-content: center;
width: 100%;
min-height: 100vh;
text-align: center;
padding: 20px;
position: relative;
background-color: #f5f5f5;
}

.recommendation-header {
margin-top: -40px;
font-size: 24px;
margin-bottom: 20px;
font-size: 26px;
font-weight: bold;
color: #333;
margin-bottom: 30px;
}

.communities {
.community-list {
display: flex;
flex-direction: row;
align-items: center;
gap: 15px;
width: 100%;
flex-wrap: wrap;
justify-content: center;
gap: 15px;
margin-bottom: 20px;
margin-bottom: 200px;
}

.communities li {
background-color: #895159;
.community-pill {
background-color: #6f4046;
color: white;
border-radius: 8px;
padding: 1px;
width: 150px;
height: 55px;
border-radius: 50px;
margin: 5px;
padding: 5px 10px;
width: 160px;
height: 50px;
text-align: center;
font-size: 17px;
font-size: 16px;
display: flex;
align-items: center;
justify-content: center;
border: none;
transition: background-color 0.3s, transform 0.2s;
box-shadow: 0 2px 5px rgba(0, 0, 0, 0.1);
}

.communities li:hover {
background-color: #6f4046;
color: white;
}

.communities li.selected {
background-color: #ffffff;
color: #6f4046;
border: 2px solid #6f4046;
.community-pill:hover {
background-color: #895159;
transform: scale(1.05);
}

.choose-more-text {
font-size: 18px;
margin-top: 50px;
font-weight: bold;
.community-pill.selected {
background-color: #ffffff;
color: #6f4046;
border: 2px solid #6f4046;
box-shadow: 0 3px 8px rgba(0, 0, 0, 0.15);
}

/* Button container and alignment */
.button-container {
position: absolute;
bottom: 70px;
right: 40px;
display: flex;
justify-content: flex-end;
width: 100%;
margin-bottom: 20px;
}

/* Button styles */
.next-button {
padding: 10px 20px;
padding: 12px 25px;
font-size: 16px;
cursor: pointer;
background-color: #466694;
width: 150px;
width: 160px;
height: 45px;
color: white;
border: none;
border-radius: 5px;
box-shadow: 0 4px 10px rgba(0, 0, 0, 0.1);
transition: background-color 0.3s, transform 0.2s;
}

.next-button:hover {
background-color: #324b73;
transform: translateY(-2px);
}

.next-button:active {
background-color: #466694;
transform: translateY(0);
}

.button-text {
text-decoration: none;
color: white;
font-weight: bold;
}
135 changes: 47 additions & 88 deletions client/src/components/login/newUser/chooseCommunityPage/index.tsx
Original file line number Diff line number Diff line change
@@ -1,103 +1,62 @@
/* eslint-disable no-console */
import React, { useEffect, useState } from 'react';
import { collection, query, getDoc, getDocs, doc, updateDoc } from 'firebase/firestore';
import { NavLink } from 'react-router-dom';
import { db } from '../../../../firebaseConfig';
import React, { useState } from 'react';
import './index.css';
import { NavLink } from 'react-router-dom';
import { auth } from '../../../../firebaseConfig';
import { updateUserCommunity } from '../../../../services/userService';
import logo from '../../../../logo.svg';
import useCommunityNames from '../../../../hooks/useCommunityNames';

/**
* Depicts communities that the user can choose from.
*/
const ChooseCommunityPage = () => {
const { communityNames } = useCommunityNames();
const [selectedCommunity, setSelectedCommunity] = useState<string>('');

const handleCommunityClick = (communityName: string) => {
setSelectedCommunity(prevCommunity => (prevCommunity === communityName ? '' : communityName));
};

const PostLoginCommunity = ({ userId }: { userId: string }) => {
const [userTags, setUserTags] = useState<string[]>([]);
const [suggestedCommunities, setSuggestedCommunities] = useState<string[]>([]);
const [selectedCommunity, setSelectedCommunity] = useState<string | null>(null);

useEffect(() => {
const fetchUserTags = async () => {
const userRef = doc(db, 'users', userId);
const docSnap = await getDoc(userRef);

if (docSnap.exists()) {
setUserTags(docSnap.data().tags || []);
} else {
console.log('User not found!');
}
};

fetchUserTags();
}, [userId]);

useEffect(() => {
if (userTags.length === 0) return;

const fetchSuggestedCommunities = async () => {
const communitiesRef = collection(db, 'communities');
const q = query(communitiesRef);

const querySnapshot = await getDocs(q);
const matchedCommunities: string[] = [];

// eslint-disable-next-line @typescript-eslint/no-shadow
querySnapshot.forEach(doc => {
const community = doc.data();
const commonTags = community.tags.filter((tag: string) => userTags.includes(tag));

// if there are common tags with a community, suggest that community -- can change
// implementation
if (commonTags.length > 0) {
matchedCommunities.push(doc.id);
}
});

setSuggestedCommunities(matchedCommunities);
};

fetchSuggestedCommunities();
}, [userTags]);

const handleCommunitySelect = async (community: string) => {
setSelectedCommunity(community);
const userRef = doc(db, 'users', userId);

const saveCommunityToUserAccount = async (community: string) => {
try {
const docSnap = await getDoc(userRef);
if (!docSnap.exists()) {
console.log('User not found!');
return;
}
const userData = docSnap.data();
const communitySelected = userData.communitySelected || [];

// users can only select one community:
if (communitySelected.length === 0 || communitySelected[0] !== community) {
await updateDoc(userRef, {
communitySelected: [community],
});
console.log(`Community "${community}" added to user's selected communities`);
const user = auth.currentUser;
if (user) {
console.log('Saving community for user:', user.email);
await updateUserCommunity(user.email!, community); // Call the backend service
console.log('Community updated successfully');
} else {
console.log(`Community "${community}" is already selected.`);
console.error('No user is logged in.');
}
} catch (error) {
console.error('Error adding community to user:', error);
console.error('Error saving community:', error);
}
};

return (
<div className='community-container'>
<h2 className='recommendation-header'>
We recommend the following communities based on your interests:
</h2>
<ul className='communities'>
{suggestedCommunities.map(community => (
<li
key={community}
onClick={() => handleCommunitySelect(community)}
className={selectedCommunity === community ? 'selected' : ''}>
{community}
</li>
))}
</ul>
<p className='choose-more-text'></p>
<img src={logo} alt='Fake Stack Overflow Logo' className='logo-login' />
<div className='recommendation-header'>
<h2>Recommended Communities:</h2>
</div>
<div className='community-list'>
{communityNames &&
communityNames.map(community => (
<li
className={`community-pill ${selectedCommunity === community.name ? 'selected' : ''}`}
key={community.name}
onClick={() => handleCommunityClick(community.name)}>
{community.name}
</li>
))}
</div>
<div className='button-container'>
<button className='next-button'>
<button
className='next-button'
onClick={() => {
console.log('Saving community:', selectedCommunity);
saveCommunityToUserAccount(selectedCommunity);
}}>
<NavLink className='button-text' to='/home'>
Next
</NavLink>
Expand All @@ -107,4 +66,4 @@ const PostLoginCommunity = ({ userId }: { userId: string }) => {
);
};

export default PostLoginCommunity;
export default ChooseCommunityPage;
17 changes: 6 additions & 11 deletions client/src/components/login/newUser/chooseTagsPage/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,9 @@
import React, { useState } from 'react';
import './index.css';
import { NavLink } from 'react-router-dom';
import { doc, updateDoc } from 'firebase/firestore';
// eslint-disable-next-line import/no-extraneous-dependencies
import useTagNames from '../../../../hooks/useTagNames';
import { db, auth } from '../../../../firebaseConfig';
import { auth } from '../../../../firebaseConfig';
import { updateUserTags } from '../../../../services/userService'; // Import the userService function
import logo from '../../../../logo.svg';

/**
Expand All @@ -29,15 +28,11 @@ const ChooseTagsPage = () => {
try {
const user = auth.currentUser;
if (user) {
console.log(user.email);
if (user.email) {
const userRef = doc(db, 'users', user.email);
await updateDoc(userRef, { tags });
} else {
console.error('Error saving tags');
}
console.log('Saving tags for user:', user.email);
await updateUserTags(user.email!, tags);
console.log('Tags updated successfully');
} else {
console.error('Error saving tags');
console.error('No user is logged in.');
}
} catch (error) {
console.error('Error saving tags:', error);
Expand Down
29 changes: 11 additions & 18 deletions client/src/components/main/profile/accountInfo/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,12 @@
/* eslint-disable no-console */
import React, { useEffect, useState } from 'react';
import './index.css';
import { doc, getDoc } from 'firebase/firestore';
import { NavLink } from 'react-router-dom';
import { auth, db } from '../../../../firebaseConfig';
import useUserContext from '../../../../hooks/useUserContext';
import { auth } from '../../../../firebaseConfig';
import { getUser } from '../../../../services/userService';

/**
* AccountInfo component which displays the user's username and password.
* AccountInfo component which displays the user's username and status.
*/
const AccountInfo = () => {
const [userData, setUserData] = useState({
Expand All @@ -18,25 +17,19 @@ const AccountInfo = () => {
status: '',
});
const [creationTime, setCreationTime] = useState<string | null>(null);
const { user } = useUserContext();

useEffect(() => {
const fetchUserData = async () => {
const firebaseUser = auth.currentUser;
if (firebaseUser && firebaseUser.email) {
try {
const userRef = doc(db, 'users', firebaseUser.email);
const userDoc = await getDoc(userRef);
if (userDoc.exists()) {
const data = userDoc.data();
setUserData({
first_name: data.first_name || '',
last_name: data.last_name || '',
username: data.username || firebaseUser.email,
status: user.status || 'low',
});
} else {
console.log('No such user!');
}
const data = await getUser(firebaseUser.email);
setUserData({
first_name: data.firstName,
last_name: data.lastName,
username: data.username,
status: data.status,
});
} catch (error) {
console.error('Error fetching user data:', error);
}
Expand Down
Loading

0 comments on commit 0de00a1

Please sign in to comment.