import { Tabs } from 'web/components/layout/tabs' import { useUser } from 'web/hooks/use-user' import React, { useEffect, useState } from 'react' import { Notification, notification_reason_types, notification_source_types, } from 'common/notification' import { listenForNotifications } from 'web/lib/firebase/notifications' import { Avatar } from 'web/components/avatar' import { Row } from 'web/components/layout/row' import { Page } from 'web/components/page' import { Title } from 'web/components/title' import { doc, updateDoc } from 'firebase/firestore' import { db } from 'web/lib/firebase/init' import { CopyLinkDateTimeComponent } from 'web/components/feed/copy-link-date-time' import { Answer } from 'common/answer' import { Comment } from 'web/lib/firebase/comments' import { getValue } from 'web/lib/firebase/utils' import Custom404 from 'web/pages/404' import { UserLink } from 'web/components/user-page' import { User } from 'common/user' import { useContract } from 'web/hooks/use-contract' import { Contract } from 'common/contract' export default function Notifications() { const user = useUser() const [notifications, setNotifications] = useState< Notification[] | undefined >() useEffect(() => { if (user) return listenForNotifications(user.id, setNotifications) }, [user]) if (!user) { // TODO: return sign in page return } // TODO: use infinite scroll return ( {notifications && notifications.map((notification) => ( ))} ), }, ]} /> ) } function Notification(props: { currentUser: User notification: Notification }) { const { notification, currentUser } = props const { sourceType, sourceContractId, sourceId, userId, id, sourceUserName, sourceUserAvatarUrl, reasonText, reason, sourceUserUsername, createdTime, } = notification const [subText, setSubText] = useState('') const contract = useContract(sourceContractId ?? '') useEffect(() => { if (!contract) return if (sourceType === 'contract') { setSubText(contract.question) } }, [contract, sourceType]) useEffect(() => { if (!sourceContractId || !sourceId) return if (sourceType === 'answer') { getValue( doc(db, `contracts/${sourceContractId}/answers/`, sourceId) ).then((answer) => { setSubText(answer?.text || '') }) } else if (sourceType === 'comment') { getValue( doc(db, `contracts/${sourceContractId}/comments/`, sourceId) ).then((comment) => { setSubText(comment?.text || '') }) } }, [sourceContractId, sourceId, sourceType]) useEffect(() => { if (!contract || !notification || notification.isSeen) return updateDoc(doc(db, `users/${currentUser.id}/notifications/`, id), { ...notification, isSeen: true, viewTime: new Date(), }) }, [notification, contract, currentUser, id, userId]) function getSourceUrl(sourceId?: string) { if (!contract) return '' return `/${contract.creatorUsername}/${ contract.slug }#${getSourceIdForLinkComponent(sourceId ?? '')}` } function getSourceIdForLinkComponent(sourceId: string) { switch (sourceType) { case 'answer': return `answer-${sourceId}` case 'comment': return sourceId case 'contract': return '' default: return sourceId } } return ( {sourceType && reason ? ( {getReasonTextFromReason(sourceType, reason, contract)} ) : ( reasonText )} {contract && sourceId && ( )} {' '} {contract && subText === contract.question ? ( {subText} ) : ( {subText} )} ) } function getReasonTextFromReason( source: notification_source_types, reason: notification_reason_types, contract: Contract | undefined ) { switch (source) { case 'comment': return `commented on ${contract?.question}` case 'contract': return `${reason} ${contract?.question}` case 'answer': return `answered ${contract?.question}` default: return '' } }