projeto-hit/frontend/src/components/NotificationsPopOver/index.js

355 lines
7.8 KiB
JavaScript
Raw Normal View History

2023-09-08 19:50:51 +00:00
import React, { useState, useRef, useEffect, useContext } from "react"
2023-09-08 19:50:51 +00:00
import { useHistory } from "react-router-dom"
import { format } from "date-fns"
import openSocket from "socket.io-client"
import useSound from "use-sound"
2023-09-08 19:50:51 +00:00
import Popover from "@material-ui/core/Popover"
//import IconButton from "@material-ui/core/IconButton";
2023-09-08 19:50:51 +00:00
import List from "@material-ui/core/List"
import ListItem from "@material-ui/core/ListItem"
import ListItemText from "@material-ui/core/ListItemText"
import { makeStyles } from "@material-ui/core/styles"
//import Badge from "@material-ui/core/Badge";
//import ChatIcon from "@material-ui/icons/Chat";
2023-09-08 19:50:51 +00:00
import TicketListItem from "../TicketListItem"
import { i18n } from "../../translate/i18n"
import useTickets from "../../hooks/useTickets"
import alertSound from "../../assets/sound.mp3"
import { AuthContext } from "../../context/Auth/AuthContext"
const useStyles = makeStyles(theme => ({
tabContainer: {
overflowY: "auto",
maxHeight: 350,
...theme.scrollbarStyles,
},
popoverPaper: {
width: "100%",
maxWidth: 350,
marginLeft: theme.spacing(2),
marginRight: theme.spacing(1),
[theme.breakpoints.down("sm")]: {
maxWidth: 270,
},
},
noShadow: {
boxShadow: "none !important",
},
}))
const NotificationsPopOver = () => {
2023-09-08 19:50:51 +00:00
const classes = useStyles()
2023-09-08 19:50:51 +00:00
const history = useHistory()
const { user } = useContext(AuthContext)
const ticketIdUrl = +history.location.pathname.split("/")[2]
const ticketIdRef = useRef(ticketIdUrl)
const anchorEl = useRef()
const [isOpen, setIsOpen] = useState(false)
const [notifications, setNotifications] = useState([])
2023-09-08 19:50:51 +00:00
const [, setDesktopNotifications] = useState([])
2023-09-08 19:50:51 +00:00
const { tickets } = useTickets({ withUnreadMessages: "true" })
const [play] = useSound(alertSound)
const soundAlertRef = useRef()
2023-09-08 19:50:51 +00:00
const historyRef = useRef(history)
2023-09-08 19:50:51 +00:00
const { handleLogout } = useContext(AuthContext)
2022-05-25 20:19:38 +00:00
// const [lastRef] = useState(+history.location.pathname.split("/")[2])
2023-09-08 19:50:51 +00:00
useEffect(() => {
2023-09-08 19:50:51 +00:00
soundAlertRef.current = play
if (!("Notification" in window)) {
} else {
2023-09-08 19:50:51 +00:00
Notification.requestPermission()
}
2023-09-08 19:50:51 +00:00
}, [play])
useEffect(() => {
2023-09-08 19:50:51 +00:00
setNotifications(tickets)
}, [tickets])
useEffect(() => {
2023-09-08 19:50:51 +00:00
ticketIdRef.current = ticketIdUrl
}, [ticketIdUrl])
useEffect(() => {
2023-09-08 19:50:51 +00:00
const socket = openSocket(process.env.REACT_APP_BACKEND_URL)
2023-09-08 19:50:51 +00:00
socket.on("reload_page", (data) => {
if (user.id === data.userId) {
2023-09-08 19:50:51 +00:00
window.location.reload(true)
2023-09-08 19:50:51 +00:00
}
})
socket.on("onlineStatus", (data) => {
2023-09-08 19:50:51 +00:00
if (data.action === "logout") {
if (`${user.id}` === data.userOnlineTime['userId']) {
socket.emit("online", { logoutUserId: user.id })
2023-09-08 19:50:51 +00:00
handleLogout()
}
}
2023-09-08 19:50:51 +00:00
})
// socket.on("isOnline", (data) => {
// if (data.action === "online") {
// if (data.userId === user.id) {
// socket.emit("online", user.id)
// }
// }
// });
if (user.profile === 'user') {
2023-09-08 19:50:51 +00:00
// if (_fifo) {
// clearInterval(_fifo);
// }
2023-09-08 19:50:51 +00:00
// _fifo = setInterval(() => {
// socket.emit("online", user.id)
// }, 3000);
2023-09-08 19:50:51 +00:00
const intID = setInterval(() => {
console.log('emitting the online')
socket.emit("online", user.id)
}, 3000)
2023-09-08 19:50:51 +00:00
return () => clearInterval(intID)
2023-09-08 19:50:51 +00:00
}
return () => {
2023-09-08 19:50:51 +00:00
socket.disconnect()
}
}, [user.id, handleLogout, user.profile])
useEffect(() => {
2023-09-08 19:50:51 +00:00
const socket = openSocket(process.env.REACT_APP_BACKEND_URL)
2023-09-08 19:50:51 +00:00
socket.on("connect", () => socket.emit("joinNotification"))
socket.on("ticket", data => {
2023-09-08 19:50:51 +00:00
if (data.action === "updateUnread" || data.action === "delete") {
2022-05-25 20:19:38 +00:00
setNotifications(prevState => {
2023-09-08 19:50:51 +00:00
const ticketIndex = prevState.findIndex(t => t.id === data.ticketId)
if (ticketIndex !== -1) {
2023-09-08 19:50:51 +00:00
prevState.splice(ticketIndex, 1)
return [...prevState]
}
2023-09-08 19:50:51 +00:00
return prevState
})
setDesktopNotifications(prevState => {
const notfiticationIndex = prevState.findIndex(
n => n.tag === String(data.ticketId)
2023-09-08 19:50:51 +00:00
)
if (notfiticationIndex !== -1) {
2023-09-08 19:50:51 +00:00
prevState[notfiticationIndex].close()
prevState.splice(notfiticationIndex, 1)
return [...prevState]
}
2023-09-08 19:50:51 +00:00
return prevState
})
}
2023-09-08 19:50:51 +00:00
})
2023-09-08 19:50:51 +00:00
socket.on("appMessage", data => {
if (
data.action === "create" &&
!data.message.read &&
(data.ticket.userId === user?.id || !data.ticket.userId)
2023-09-08 19:50:51 +00:00
) {
2022-05-25 20:19:38 +00:00
2023-09-08 19:50:51 +00:00
setNotifications(prevState => {
2022-05-25 20:19:38 +00:00
2023-09-08 19:50:51 +00:00
const ticketIndex = prevState.findIndex(t => t.id === data.ticket.id)
if (ticketIndex !== -1) {
2023-09-08 19:50:51 +00:00
prevState[ticketIndex] = data.ticket
return [...prevState]
}
2023-09-08 19:50:51 +00:00
return [data.ticket, ...prevState]
})
2022-05-25 20:19:38 +00:00
const shouldNotNotificate = (data.message.ticketId === ticketIdRef.current && document.visibilityState === "visible") ||
(data.ticket.userId && data.ticket.userId !== user?.id) ||
2023-09-08 19:50:51 +00:00
data.ticket.isGroup || !data.ticket.userId
2023-09-08 19:50:51 +00:00
if (shouldNotNotificate) return
2023-09-08 19:50:51 +00:00
handleNotifications(data)
}
2023-09-08 19:50:51 +00:00
})
socket.on('notifyPeding', data =>{
handleNotifications("", data);
});
return () => {
2023-09-08 19:50:51 +00:00
socket.disconnect()
}
}, [user])
const handleNotifications = (data, notify) => {
let isQueue = false;
if(!notify){
const { message, contact, ticket } = data
const options = {
body: `${message.body} - ${format(new Date(), "HH:mm")}`,
icon: contact.profilePicUrl,
tag: ticket.id,
renotify: true,
}
const notification = new Notification(
`${i18n.t("tickets.notification.message")} ${contact.name}`,
options
)
notification.onclick = e => {
e.preventDefault()
window.focus()
historyRef.current.push(`/tickets/${ticket.id}`)
}
setDesktopNotifications(prevState => {
const notfiticationIndex = prevState.findIndex(
n => n.tag === notification.tag
)
if (notfiticationIndex !== -1) {
prevState[notfiticationIndex] = notification
return [...prevState]
}
return [notification, ...prevState]
})
}else{
user.queues.forEach(queue =>{
if(queue.id === notify.data.queue?.id){
isQueue = true;
}
})
}
if(!isQueue && notify){
return;
}else{
const notification = new Notification(`${i18n.t("tickets.notification.messagePeding")} ${notify.data.queue?.name}`);
notification.onclick = e => {
e.preventDefault()
window.focus()
historyRef.current.push(`/tickets`)
}
setDesktopNotifications(prevState => {
const notfiticationIndex = prevState.findIndex(
n => n.tag === notification.tag
)
if (notfiticationIndex !== -1) {
prevState[notfiticationIndex] = notification
return [...prevState]
}
return [notification, ...prevState]
})
}
2023-09-08 19:50:51 +00:00
soundAlertRef.current()
}
// const handleClick = () => {
// setIsOpen(prevState => !prevState);
// };
const handleClickAway = () => {
2023-09-08 19:50:51 +00:00
setIsOpen(false)
}
const NotificationTicket = ({ children }) => {
2023-09-08 19:50:51 +00:00
return <div onClick={handleClickAway}>{children}</div>
}
return (
<>
{/* <IconButton
onClick={handleClick}
// buttonRef={anchorEl}
ref={anchorEl}
aria-label="Open Notifications"
color="inherit"
>
<Badge badgeContent={notifications.length} color="secondary">
<ChatIcon />
</Badge>
</IconButton> */}
<Popover
disableScrollLock
open={isOpen}
anchorEl={anchorEl.current}
anchorOrigin={{
vertical: "bottom",
horizontal: "right",
}}
transformOrigin={{
vertical: "top",
horizontal: "right",
}}
classes={{ paper: classes.popoverPaper }}
onClose={handleClickAway}
>
<List dense className={classes.tabContainer}>
{notifications.length === 0 ? (
<ListItem>
<ListItemText>{i18n.t("notifications.noTickets")}</ListItemText>
</ListItem>
) : (
2022-05-25 20:19:38 +00:00
notifications.map(ticket => (
<NotificationTicket key={ticket.id}>
<TicketListItem ticket={ticket} />
</NotificationTicket>
))
)}
</List>
2022-05-25 20:19:38 +00:00
</Popover>
</>
2023-09-08 19:50:51 +00:00
)
}
2023-09-08 19:50:51 +00:00
export default NotificationsPopOver