diff --git a/backend/src/httpServer.ts b/backend/src/httpServer.ts index c6f196d9..23288624 100644 --- a/backend/src/httpServer.ts +++ b/backend/src/httpServer.ts @@ -16,4 +16,4 @@ importInitialData().then((res) => console.log(res)); app.use("/users", usersRouter); app.use("/auth", authRouter); app.use("/chat", chatRouter); -app.use("/room", roomRouter); \ No newline at end of file +app.use("/room", roomRouter); diff --git a/backend/src/routes/roomRoute.ts b/backend/src/routes/roomRoute.ts index d5d2abfd..419e1ddd 100644 --- a/backend/src/routes/roomRoute.ts +++ b/backend/src/routes/roomRoute.ts @@ -4,64 +4,72 @@ import driver from "../driver/driver"; const roomRouter = Router(); roomRouter.get("/:userId", async (req, res) => { - try { - const userId = req.params.userId; - const session = driver.session(); - const roomsQuery = await session.run(` + try { + const userId = req.params.userId; + const session = driver.session(); + const roomsQuery = await session.run( + ` MATCH (room:Room)-[:INVITED]-(u:User {id: $userId}) RETURN room - `, {userId}); - await session.close(); - const rooms = roomsQuery.records.map((record) => record.get("room").properties).map(record => ({ - ...record, - title: "Join meeting", - })); - return res.json({status: "ok", rooms}); - } catch (err) { - console.log("Error:", err); - return res.status(404).json({ status: "error", errors: err as object }); - } + `, + { userId }, + ); + await session.close(); + const rooms = roomsQuery.records + .map((record) => record.get("room").properties) + .map((record) => ({ + ...record, + title: "Join meeting", + })); + return res.json({ status: "ok", rooms }); + } catch (err) { + console.log("Error:", err); + return res.status(404).json({ status: "error", errors: err as object }); + } }); roomRouter.post("/", async (req, res) => { - try { - const newRoomProps = req.body; - const {roomId, from, to} = newRoomProps; - const session = driver.session(); - const areFriends = await isFriend(session, from, to); - if (!areFriends) { - await session.close(); - return res - .status(400) - .json({ status: "error", errors: { id: "no friends" } }); - } - await session.run(`CREATE (r: Room $room)`, {room: newRoomProps}); - await session.run(` + try { + const newRoomProps = req.body; + const { roomId, from, to } = newRoomProps; + const session = driver.session(); + const areFriends = await isFriend(session, from, to); + if (!areFriends) { + await session.close(); + return res + .status(400) + .json({ status: "error", errors: { id: "no friends" } }); + } + await session.run(`CREATE (r: Room $room)`, { room: newRoomProps }); + await session.run( + ` MATCH (u:User {id: $userId}) MATCH (r:Room {roomId: $roomId}) CREATE (r)-[:INVITED]->(u) - `, {userId: to, roomId}); - await session.close(); - return res.json({status: "ok"}); - } catch (err) { - console.log("Error:", err); - return res.status(404).json({ status: "error", errors: err as object }); - } + `, + { userId: to, roomId }, + ); + await session.close(); + return res.json({ status: "ok" }); + } catch (err) { + console.log("Error:", err); + return res.status(404).json({ status: "error", errors: err as object }); + } }); - roomRouter.delete("/:roomId", async (req, res) => { - try { - const roomId = req.params.roomId; - const session = driver.session(); - await session.run(`MATCH (r:Room {roomId: $roomId}) DETACH DELETE r`, {roomId}); - await session.close(); - return res.json({status: "ok"}); - } catch (err) { - console.log("Error:", err); - return res.status(404).json({ status: "error", errors: err as object }); - } + try { + const roomId = req.params.roomId; + const session = driver.session(); + await session.run(`MATCH (r:Room {roomId: $roomId}) DETACH DELETE r`, { + roomId, + }); + await session.close(); + return res.json({ status: "ok" }); + } catch (err) { + console.log("Error:", err); + return res.status(404).json({ status: "error", errors: err as object }); + } }); - -export default roomRouter; \ No newline at end of file +export default roomRouter; diff --git a/backend/src/socketServer.ts b/backend/src/socketServer.ts index 28485384..b9544ff4 100644 --- a/backend/src/socketServer.ts +++ b/backend/src/socketServer.ts @@ -143,28 +143,30 @@ io.on("connection", async (socket: Socket) => { }); }); - socket.on("newRoom", async ({roomId, from, to, userName}) => { + socket.on("newRoom", async ({ roomId, from, to, userName }) => { await socket.join(roomId); const session = driver.session(); const userSockets = await getAllSockets(session, to); - userSockets.forEach(userSocket => { + userSockets.forEach((userSocket) => { socket.to(userSocket.id).emit("newRoom", { from, roomId, title: "Join room", to, - userName + userName, }); }); await session.close(); }); - socket.on("joinRoom", async ({roomId, peerId, userId, fullName}) => { + socket.on("joinRoom", async ({ roomId, peerId, userId, fullName }) => { await socket.join(roomId); - socket.to(roomId).emit("userConnected", {peerId, userId, fullName, socketId: socket.id}); + socket + .to(roomId) + .emit("userConnected", { peerId, userId, fullName, socketId: socket.id }); }); - socket.on("leftRoom", async ({userId, roomId}) => { + socket.on("leftRoom", async ({ userId, roomId }) => { await socket.join(roomId); socket.to(roomId).emit("leftRoom", userId); }); diff --git a/frontend/src/components/Notification.tsx b/frontend/src/components/Notification.tsx index 697442ca..ea16af3b 100644 --- a/frontend/src/components/Notification.tsx +++ b/frontend/src/components/Notification.tsx @@ -2,28 +2,32 @@ import RoomNotification from "../models/RoomNotification"; import { FontAwesomeIcon } from "@fortawesome/react-fontawesome"; import { faTrash, faVideo } from "@fortawesome/free-solid-svg-icons"; interface NotificationProps { - roomNotification: RoomNotification; - handleRoomInvite: (id: string) => void; - declineInvite: (id: string) => void; + roomNotification: RoomNotification; + handleRoomInvite: (id: string) => void; + declineInvite: (id: string) => void; } -function Notification({roomNotification, handleRoomInvite, declineInvite}: NotificationProps) { - return ( -
- {roomNotification.userName} has invited you to meeting - - -
- ) +function Notification({ + roomNotification, + handleRoomInvite, + declineInvite, +}: NotificationProps) { + return ( +
+ {roomNotification.userName} has invited you to meeting + + +
+ ); } -export default Notification; \ No newline at end of file +export default Notification; diff --git a/frontend/src/components/PeerInvite.tsx b/frontend/src/components/PeerInvite.tsx index 5cb1a42c..2e6d39a6 100644 --- a/frontend/src/components/PeerInvite.tsx +++ b/frontend/src/components/PeerInvite.tsx @@ -1,36 +1,35 @@ import User from "../models/User"; export interface PeerInviteProps { - friend: User; - inviteFriendToRoom: (id: string) => void; + friend: User; + inviteFriendToRoom: (id: string) => void; } - -function PeerInvite({friend, inviteFriendToRoom}: PeerInviteProps) { - return ( -
  • - -
    -

    - - {" "} - {friend.first_name} {friend.last_name}{" "} - -

    -
    - -
    + +function PeerInvite({ friend, inviteFriendToRoom }: PeerInviteProps) { + return ( +
  • + +
    +

    + + {" "} + {friend.first_name} {friend.last_name}{" "} + +

    +
    +
    -
  • - ); - } - + + + ); +} + export default PeerInvite; - \ No newline at end of file diff --git a/frontend/src/components/RoomPeerVideo.tsx b/frontend/src/components/RoomPeerVideo.tsx index 1b9c03bb..c4711545 100644 --- a/frontend/src/components/RoomPeerVideo.tsx +++ b/frontend/src/components/RoomPeerVideo.tsx @@ -1,32 +1,34 @@ import { useEffect, useRef, useState } from "react"; import dataService from "../services/data"; interface RoomPeerVideoProps { - remoteStream: MediaStream; - peerId: string; + remoteStream: MediaStream; + peerId: string; } -function RoomPeerVideo({remoteStream, peerId}: RoomPeerVideoProps) { - const remoteRef = useRef(null); - const [name, setName] = useState(""); - const fetchFullName = async () => { - const fullNameRequest = await dataService.fetchData(`/users/${peerId}/name`, "GET", {}); - const fullName = fullNameRequest.fullName; - setName(fullName); +function RoomPeerVideo({ remoteStream, peerId }: RoomPeerVideoProps) { + const remoteRef = useRef(null); + const [name, setName] = useState(""); + const fetchFullName = async () => { + const fullNameRequest = await dataService.fetchData( + `/users/${peerId}/name`, + "GET", + {}, + ); + const fullName = fullNameRequest.fullName; + setName(fullName); + }; + useEffect(() => { + if (remoteStream) { + remoteRef.current!.srcObject = remoteStream; + remoteRef.current!.play(); } - useEffect(() => { - if (remoteStream) { - remoteRef.current!.srcObject = remoteStream; - remoteRef.current!.play(); - } - fetchFullName(); - }, []); - return ( -
    - -
    {name}
    -
    - ) + fetchFullName(); + }, []); + return ( +
    + +
    {name}
    +
    + ); } -export default RoomPeerVideo; \ No newline at end of file +export default RoomPeerVideo; diff --git a/frontend/src/media/fetchUserMedia.ts b/frontend/src/media/fetchUserMedia.ts index cf639bea..8eb24608 100644 --- a/frontend/src/media/fetchUserMedia.ts +++ b/frontend/src/media/fetchUserMedia.ts @@ -1,9 +1,9 @@ async function fetchUserMedia() { - const localStream = await navigator.mediaDevices.getUserMedia({ - video: true, - audio: true - }); - return localStream; + const localStream = await navigator.mediaDevices.getUserMedia({ + video: true, + audio: true, + }); + return localStream; } -export default fetchUserMedia; \ No newline at end of file +export default fetchUserMedia; diff --git a/frontend/src/models/RoomNotification.ts b/frontend/src/models/RoomNotification.ts index 8fb7657e..fcdea96a 100644 --- a/frontend/src/models/RoomNotification.ts +++ b/frontend/src/models/RoomNotification.ts @@ -1,8 +1,8 @@ interface RoomNotification { - from: string; - roomId: string; - title: string; - to: string; - userName: string; + from: string; + roomId: string; + title: string; + to: string; + userName: string; } -export default RoomNotification; \ No newline at end of file +export default RoomNotification; diff --git a/frontend/src/models/RoomPeer.ts b/frontend/src/models/RoomPeer.ts index 31d77813..834d8b7e 100644 --- a/frontend/src/models/RoomPeer.ts +++ b/frontend/src/models/RoomPeer.ts @@ -1,6 +1,6 @@ interface RoomPeer { - peerId?: string; - stream: MediaStream; - fullName?: string; + peerId?: string; + stream: MediaStream; + fullName?: string; } -export default RoomPeer; \ No newline at end of file +export default RoomPeer; diff --git a/frontend/src/pages/FriendsPage.tsx b/frontend/src/pages/FriendsPage.tsx index aa4c0247..f98549f1 100644 --- a/frontend/src/pages/FriendsPage.tsx +++ b/frontend/src/pages/FriendsPage.tsx @@ -20,7 +20,7 @@ import { v4 } from "uuid"; function FriendsPage() { const navigate = useNavigate(); - + const { user, meeting, createMeeting, joinMeeting } = useUser(); const friends: User[] = useSelector((state: RootState) => state.friends); @@ -106,7 +106,7 @@ function FriendsPage() { const createRoom = () => { const roomId = v4(); navigate(`/room/${roomId}`); - } + }; useEffect(() => { if (meeting?.id) { diff --git a/frontend/src/pages/NotificationsPage.tsx b/frontend/src/pages/NotificationsPage.tsx index 18d420cd..0b03029f 100644 --- a/frontend/src/pages/NotificationsPage.tsx +++ b/frontend/src/pages/NotificationsPage.tsx @@ -10,38 +10,41 @@ import Peer from "peerjs"; import Notification from "../components/Notification"; import deleteNotification from "../redux/actions/deleteNotification"; function NotificationsPage() { - const {socket, userId, user} = useUser(); - const navigate = useNavigate(); - const dispatch = useDispatch(); - const roomNotifications: RoomNotification[] = useSelector((state: RootState) => state.notifications); - const peer: Peer = useSelector((state: RootState) => state.peer); - const handleRoomInvite = async (roomId: string) => { - await dataService.fetchData(`/room/${roomId}`, "DELETE", {}); - const fullName = `${user?.first_name} ${user?.last_name}`; - socket?.emit("joinRoom", {roomId, peerId: peer.id, userId, fullName}); - navigate(`/room/${roomId}`); - } + const { socket, userId, user } = useUser(); + const navigate = useNavigate(); + const dispatch = useDispatch(); + const roomNotifications: RoomNotification[] = useSelector( + (state: RootState) => state.notifications, + ); + const peer: Peer = useSelector((state: RootState) => state.peer); + const handleRoomInvite = async (roomId: string) => { + await dataService.fetchData(`/room/${roomId}`, "DELETE", {}); + const fullName = `${user?.first_name} ${user?.last_name}`; + socket?.emit("joinRoom", { roomId, peerId: peer.id, userId, fullName }); + navigate(`/room/${roomId}`); + }; - const declineInvite = (inviteId: string) => { - dispatch(deleteNotification(inviteId)); - } - - return ( - <> - -
    - {roomNotifications.length > 0 ? - roomNotifications.map(notification => - ) - : null} -
    -