bit of work on friends

This commit is contained in:
Mikayla Dobson
2023-02-13 19:25:28 -06:00
parent 7bd29e4dba
commit fc1046bad5
7 changed files with 129 additions and 28 deletions

View File

@@ -22,6 +22,7 @@ import GroceryListCollection from './components/pages/GroceryListCollection';
import { TokenType } from './util/types';
import './sass/App.scss';
import handleToken from './util/handleToken';
import AddFriends from './components/pages/AddFriends';
function App() {
const { setUser, token, setToken } = useAuthContext();
@@ -54,6 +55,7 @@ function App() {
<Route path="/profile" element={<Profile />} />
<Route path="/collections" element={<CollectionBrowser />} />
<Route path="/collections/:id" element={<Collection />} />
<Route path="/add-friends" element={<AddFriends />} />
<Route path="/explore" element={<Browser header="" searchFunction={() => {}} />} />
<Route path="/recipe/:id" element={<Recipe />} />
<Route path="/subscriptions" element={<Subscriptions />} />

View File

@@ -0,0 +1,22 @@
import Protect from "../../util/Protect"
import { Divider, Panel } from "../ui"
import FriendSearchWidget from "../ui/Widgets/NewFriendWidget"
const AddFriends = () => {
return (
<Protect>
<h1>Search for New Friends</h1>
<Divider />
<Panel>
<h2>Use the widget below to search for new friends!</h2>
<Divider />
<FriendSearchWidget />
</Panel>
</Protect>
)
}
export default AddFriends

View File

@@ -55,6 +55,7 @@ const LoggedIn = () => {
dropdownActive && (
<Dropdown extraStyles="top-menu-bar actions-bar">
<Button onClick={() => handleOptionSelect('/add-recipe')}>Add a Recipe</Button>
<Button onClick={() => handleOptionSelect("/add-friends")}>Add Friends</Button>
<Button onClick={() => handleOptionSelect('/collections')}>My Collections</Button>
<Button onClick={() => handleOptionSelect('/subscriptions')}>Subscriptions</Button>
<Button onClick={() => handleOptionSelect('/profile')}>Profile</Button>

View File

@@ -1,31 +1,38 @@
import { useEffect, useState } from "react";
import { addFriend, getPendingFriendRequests } from "../../util/apiUtils";
import { useAuthContext } from "../../context/AuthContext";
import API from "../../util/API";
// import { addFriend, getPendingFriendRequests } from "../../util/apiUtils";
import { UserCardType } from "../../util/types";
import Button from "./Button";
import Card from "./Card";
const UserCard: UserCardType = ({ extraStyles, user, canAdd = false, liftData }) => {
const [shouldDisable, setShouldDisable] = useState<boolean>(canAdd);
const UserCard: UserCardType = ({ extraStyles, user }) => {
const { token } = useAuthContext();
useEffect(() => {
if (!token) return;
(async function() {
const requestsOpen = await getPendingFriendRequests();
const friends = new API.Friendship(token);
const requestsOpen = await friends.getPendingFriendRequests();
console.log(requestsOpen);
if (!requestsOpen) return;
for (let req of requestsOpen) {
if (req.targetid == user.id) {
setShouldDisable(true);
console.log('should disable');
return;
}
}
setShouldDisable(false);
})();
console.log('should not disable');
});
}, [])
const handleClick = async () => {
const { id } = user;
const request = await addFriend(id!.toString());
if (!token) return;
const friends = new API.Friendship(token);
const request = await friends.addFriend(user.id!.toString());
if (request) console.log("Friend request sent to " + user.firstname);
}
@@ -34,7 +41,7 @@ const UserCard: UserCardType = ({ extraStyles, user, canAdd = false, liftData })
<div className="avatar"></div>
<h3>{user.firstname} {user.lastname.substring(0,1)}.</h3>
<h4>@{user.handle}</h4>
{ canAdd && <Button disabledText={"Request Sent"} disabled={shouldDisable} onClick={handleClick}>Add Me</Button> }
<Button disabledText={"Request Sent"} onClick={handleClick}>Add Me</Button>
</Card>
)
}

View File

@@ -0,0 +1,60 @@
import { ChangeEvent, FC, useCallback, useEffect, useState } from "react";
import { IUser } from "../../../schemas";
import { TextField, UserCard } from "..";
import { v4 } from "uuid";
import API from "../../../util/API";
import { useAuthContext } from "../../../context/AuthContext";
const FriendSearchWidget: FC<{}> = () => {
const { token } = useAuthContext();
const [searchTerm, setSearchTerm] = useState<string>();
const [userPool, setUserPool] = useState<IUser[]>([]);
const [pendingRequests, setPendingRequests] = useState();
const [friendResults, setFriendResults] = useState<IUser[]>([]);
// load available user pool on mount
useEffect(() => {
if (!token) return;
(async function() {
const users = new API.User(token);
const result = await users.getAll();
if (result) setUserPool(result);
})();
(async function() {
const friends = new API.Friendship(token);
const result = await friends.getAll();
setFriendResults(result);
})();
}, [])
useEffect(() => {
console.log(searchTerm);
searchTerm && setUserPool((prev) => {
const newPool = prev.filter(person => {
if (person.firstname.toLowerCase().includes(searchTerm) || person.lastname.toLowerCase().includes(searchTerm) || person.handle.toLowerCase().includes(searchTerm)) return person;
})
return newPool;
})
}, [searchTerm])
useEffect(() => {
console.log(userPool);
}, [userPool])
return (
<div id="friend-search-widget">
<TextField onChange={(e: ChangeEvent<HTMLInputElement>) => setSearchTerm(e.target.value.toLowerCase())} placeholder={'Search'} />
{
userPool.map((friend: IUser) => {
return <UserCard key={v4()} user={friend} canAdd liftData={() => {}} />
})
}
</div>
)
}
export default FriendSearchWidget;

View File

@@ -1,4 +1,4 @@
import { AxiosHeaders, AxiosRequestHeaders, AxiosResponse } from "axios";
import { AxiosError, AxiosHeaders, AxiosRequestHeaders, AxiosResponse } from "axios";
import { IUser, IUserAuth, IFriendship, IRecipe, IIngredient, ICollection, IGroceryList } from "../schemas";
import { default as _instance } from "./axiosInstance";
@@ -138,13 +138,31 @@ module API {
export class Friendship extends RestController<IFriendship> {
constructor(token: string) {
super(Settings.getAPISTRING() + "/app/friends", token);
super(Settings.getAPISTRING() + "/app/friend", token);
}
override async getAll() {
try {
const response = await this.instance.get(this.endpoint, this.headers);
return Promise.resolve(response.data);
} catch(e) {
const error = e as AxiosError;
if (error.response?.status == 404) {
console.log('no friends found');
return [];
}
}
}
async getPendingFriendRequests() {
const response = await this.instance.get(this.endpoint + "?pending=true", this.headers);
return Promise.resolve(response.data);
}
async addFriend(id: string | number) {
const response = await this.instance.post(this.endpoint + `/${id}`, this.headers);
return Promise.resolve(response.data);
}
}
export class Recipe extends RestController<IRecipe> {

View File

@@ -9,19 +9,8 @@ const router = Router();
export const friendRouter = (app: Express) => {
app.use('/app/friend', router);
router.use((req, res, next) => {
let test = req.session.user;
if (req.session.user == undefined) {
throw new Error("No session found");
} else {
const narrowed = req.session.user;
next();
}
})
router.post('/:targetid', restrictAccess, async (req, res, next) => {
const user = req.session.user as IUser;
const user = req.user as IUser;
const { targetid } = req.params;
try {
@@ -34,7 +23,7 @@ export const friendRouter = (app: Express) => {
// get all friendships for a user
router.get('/', async (req, res, next) => {
const user = req.session.user as IUser;
const user = req.user as IUser;
const { pending } = req.query;
try {
@@ -53,7 +42,7 @@ export const friendRouter = (app: Express) => {
// get one friendship by its id
router.get('/:id', async (req, res, next) => {
const { id } = req.params;
const user = req.session.user as IUser;
const user = req.user as IUser;
try {
const { code, data } = await UserInstance.getFriendshipByID(id, user.id as number);
@@ -76,7 +65,7 @@ export const friendRouter = (app: Express) => {
router.put('/:id', async (req, res, next) => {
const data = req.body;
const { id } = req.params;
const user = req.session.user as IUser;
const user = req.user as IUser;
try {
const response = await UserInstance.updateFriendship(id, user.id as number, data);
@@ -85,4 +74,6 @@ export const friendRouter = (app: Express) => {
next(e);
}
})
return router;
}