bug: fix notifications

This commit is contained in:
Kieran 2023-02-07 16:10:31 +00:00
parent 1e76e729f7
commit 015f799cf7
Signed by: Kieran
GPG Key ID: DE71CEB3925BE941
3 changed files with 20 additions and 13 deletions

View File

@ -6,7 +6,7 @@ import { TaggedRawEvent, HexKey, Lists } from "Nostr";
import EventKind from "Nostr/EventKind"; import EventKind from "Nostr/EventKind";
import Event from "Nostr/Event"; import Event from "Nostr/Event";
import { Subscriptions } from "Nostr/Subscriptions"; import { Subscriptions } from "Nostr/Subscriptions";
import { addDirectMessage, setFollows, setRelays, setMuted, setBlocked, sendNotification } from "State/Login"; import { addDirectMessage, setFollows, setRelays, setMuted, setBlocked, sendNotification, setLatestNotifications } from "State/Login";
import { RootState } from "State/Store"; import { RootState } from "State/Store";
import { mapEventToProfile, MetadataCache } from "State/Users"; import { mapEventToProfile, MetadataCache } from "State/Users";
import { useDb } from "State/Users/Db"; import { useDb } from "State/Users/Db";
@ -20,7 +20,7 @@ import useModeration from "Hooks/useModeration";
*/ */
export default function useLoginFeed() { export default function useLoginFeed() {
const dispatch = useDispatch(); const dispatch = useDispatch();
const { publicKey: pubKey, privateKey: privKey, latestMuted } = useSelector((s: RootState) => s.login); const { publicKey: pubKey, privateKey: privKey, latestMuted, readNotifications } = useSelector((s: RootState) => s.login);
const { isMuted } = useModeration(); const { isMuted } = useModeration();
const db = useDb(); const db = useDb();
@ -116,8 +116,10 @@ export default function useLoginFeed() {
}, [dispatch, metadataFeed.store, db]); }, [dispatch, metadataFeed.store, db]);
useEffect(() => { useEffect(() => {
const replies = notificationFeed.store.notes.filter(a => a.kind === EventKind.TextNote && !isMuted(a.pubkey)) const replies = notificationFeed.store.notes.
filter(a => a.kind === EventKind.TextNote && !isMuted(a.pubkey) && a.created_at > readNotifications)
replies.forEach(nx => { replies.forEach(nx => {
dispatch(setLatestNotifications(nx.created_at));
makeNotification(db, nx).then(notification => { makeNotification(db, nx).then(notification => {
if (notification) { if (notification) {
// @ts-ignore // @ts-ignore
@ -125,7 +127,7 @@ export default function useLoginFeed() {
} }
}) })
}) })
}, [dispatch, notificationFeed.store, db]); }, [dispatch, notificationFeed.store, db, readNotifications]);
useEffect(() => { useEffect(() => {
const muted = getMutedKeys(mutedFeed.store.notes) const muted = getMutedKeys(mutedFeed.store.notes)

View File

@ -27,9 +27,9 @@ export default function Layout() {
const [show, setShow] = useState(false) const [show, setShow] = useState(false)
const dispatch = useDispatch(); const dispatch = useDispatch();
const navigate = useNavigate(); const navigate = useNavigate();
const { loggedOut, publicKey, relays, notifications, readNotifications, dms, preferences, newUserKey } = useSelector((s: RootState) => s.login); const { loggedOut, publicKey, relays, latestNotification, readNotifications, dms, preferences, newUserKey } = useSelector((s: RootState) => s.login);
const { isMuted } = useModeration(); const { isMuted } = useModeration();
const filteredDms = dms.filter(a => !isMuted(a.pubkey))
const usingDb = useDb(); const usingDb = useDb();
const pub = useEventPublisher(); const pub = useEventPublisher();
useLoginFeed(); useLoginFeed();
@ -39,6 +39,9 @@ export default function Layout() {
return hideNoteCreator.some(a => location.pathname.startsWith(a)); return hideNoteCreator.some(a => location.pathname.startsWith(a));
}, [location]); }, [location]);
const hasNotifications = useMemo(() => latestNotification > readNotifications, [latestNotification, readNotifications]);
const unreadDms = useMemo(() => publicKey ? totalUnread(dms.filter(a => !isMuted(a.pubkey)), publicKey) : 0, [dms, publicKey]);
useEffect(() => { useEffect(() => {
System.nip42Auth = pub.nip42Auth System.nip42Auth = pub.nip42Auth
}, [pub]) }, [pub])
@ -153,8 +156,6 @@ export default function Layout() {
} }
function accountHeader() { function accountHeader() {
const unreadNotifications = notifications?.filter(a => (a.created_at * 1000) > readNotifications).length;
const unreadDms = publicKey ? totalUnread(filteredDms, publicKey) : 0;
return ( return (
<div className="header-actions"> <div className="header-actions">
<div className="btn btn-rnd" onClick={(e) => navigate("/search")}> <div className="btn btn-rnd" onClick={(e) => navigate("/search")}>
@ -166,7 +167,7 @@ export default function Layout() {
</div> </div>
<div className="btn btn-rnd" onClick={(e) => goToNotifications(e)}> <div className="btn btn-rnd" onClick={(e) => goToNotifications(e)}>
<Bell /> <Bell />
{unreadNotifications > 0 && (<span className="has-unread"></span>)} {hasNotifications && (<span className="has-unread"></span>)}
</div> </div>
<ProfileImage pubkey={publicKey || ""} showUsername={false} /> <ProfileImage pubkey={publicKey || ""} showUsername={false} />
</div> </div>

View File

@ -126,9 +126,9 @@ export interface LoginStore {
blocked: HexKey[], blocked: HexKey[],
/** /**
* Notifications for this login session * Latest notification
*/ */
notifications: TaggedRawEvent[], latestNotification: number,
/** /**
* Timestamp of last read notification * Timestamp of last read notification
@ -170,7 +170,7 @@ export const InitState = {
muted: [], muted: [],
blocked: [], blocked: [],
latestMuted: 0, latestMuted: 0,
notifications: [], latestNotification: 0,
readNotifications: new Date().getTime(), readNotifications: new Date().getTime(),
dms: [], dms: [],
dmInteraction: 0, dmInteraction: 0,
@ -362,9 +362,12 @@ const LoginSlice = createSlice({
window.localStorage.setItem(RelayListKey, JSON.stringify(relays)); window.localStorage.setItem(RelayListKey, JSON.stringify(relays));
}, },
markNotificationsRead: (state) => { markNotificationsRead: (state) => {
state.readNotifications = new Date().getTime(); state.readNotifications = Math.ceil(new Date().getTime() / 1000);
window.localStorage.setItem(NotificationsReadItem, state.readNotifications.toString()); window.localStorage.setItem(NotificationsReadItem, state.readNotifications.toString());
}, },
setLatestNotifications: (state, action: PayloadAction<number>) => {
state.latestNotification = action.payload;
},
setPreferences: (state, action: PayloadAction<UserPreferences>) => { setPreferences: (state, action: PayloadAction<UserPreferences>) => {
state.preferences = action.payload; state.preferences = action.payload;
window.localStorage.setItem(UserPreferencesKey, JSON.stringify(state.preferences)); window.localStorage.setItem(UserPreferencesKey, JSON.stringify(state.preferences));
@ -386,6 +389,7 @@ export const {
incDmInteraction, incDmInteraction,
logout, logout,
markNotificationsRead, markNotificationsRead,
setLatestNotifications,
setPreferences, setPreferences,
} = LoginSlice.actions; } = LoginSlice.actions;