notifications migrated to pinia
This commit is contained in:
parent
21319d3e52
commit
a196ed88e8
11 changed files with 122 additions and 146 deletions
|
|
@ -1,9 +1,9 @@
|
||||||
import { defineAsyncComponent } from 'vue'
|
import { defineAsyncComponent } from 'vue'
|
||||||
|
|
||||||
import { notificationsFromStore } from '../../services/notification_utils/notification_utils.js'
|
|
||||||
import BasicUserCard from '../basic_user_card/basic_user_card.vue'
|
import BasicUserCard from '../basic_user_card/basic_user_card.vue'
|
||||||
|
|
||||||
import { useMergedConfigStore } from 'src/stores/merged_config.js'
|
import { useMergedConfigStore } from 'src/stores/merged_config.js'
|
||||||
|
import { useNotificationsStore } from 'src/stores/notifications.js'
|
||||||
import { useOAuthStore } from 'src/stores/oauth.js'
|
import { useOAuthStore } from 'src/stores/oauth.js'
|
||||||
|
|
||||||
import { approveUser, denyUser } from 'src/api/user.js'
|
import { approveUser, denyUser } from 'src/api/user.js'
|
||||||
|
|
@ -24,7 +24,7 @@ const FollowRequestCard = {
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
findFollowRequestNotificationId() {
|
findFollowRequestNotificationId() {
|
||||||
const notif = notificationsFromStore(this.$store).find(
|
const notif = useNotificationsStore().data.find(
|
||||||
(notif) =>
|
(notif) =>
|
||||||
notif.from_profile.id === this.user.id &&
|
notif.from_profile.id === this.user.id &&
|
||||||
notif.type === 'follow_request',
|
notif.type === 'follow_request',
|
||||||
|
|
|
||||||
|
|
@ -5,7 +5,7 @@ import NavigationPins from 'src/components/navigation/navigation_pins.vue'
|
||||||
import GestureService from '../../services/gesture_service/gesture_service'
|
import GestureService from '../../services/gesture_service/gesture_service'
|
||||||
import {
|
import {
|
||||||
countExtraNotifications,
|
countExtraNotifications,
|
||||||
unseenNotificationsFromStore,
|
unseenNotifications,
|
||||||
} from '../../services/notification_utils/notification_utils'
|
} from '../../services/notification_utils/notification_utils'
|
||||||
|
|
||||||
import { useAnnouncementsStore } from 'src/stores/announcements.js'
|
import { useAnnouncementsStore } from 'src/stores/announcements.js'
|
||||||
|
|
@ -57,8 +57,7 @@ const MobileNav = {
|
||||||
return useUsersStore().currentUser
|
return useUsersStore().currentUser
|
||||||
},
|
},
|
||||||
unseenNotifications() {
|
unseenNotifications() {
|
||||||
return unseenNotificationsFromStore(
|
return unseenNotifications(
|
||||||
this.$store,
|
|
||||||
useMergedConfigStore().mergedConfig.notificationVisibility,
|
useMergedConfigStore().mergedConfig.notificationVisibility,
|
||||||
useMergedConfigStore().mergedConfig.ignoreInactionableSeen,
|
useMergedConfigStore().mergedConfig.ignoreInactionableSeen,
|
||||||
)
|
)
|
||||||
|
|
|
||||||
|
|
@ -7,9 +7,8 @@ import FaviconService from '../../services/favicon_service/favicon_service.js'
|
||||||
import {
|
import {
|
||||||
ACTIONABLE_NOTIFICATION_TYPES,
|
ACTIONABLE_NOTIFICATION_TYPES,
|
||||||
countExtraNotifications,
|
countExtraNotifications,
|
||||||
filteredNotificationsFromStore,
|
filteredNotifications,
|
||||||
notificationsFromStore,
|
unseenNotifications,
|
||||||
unseenNotificationsFromStore,
|
|
||||||
} from '../../services/notification_utils/notification_utils.js'
|
} from '../../services/notification_utils/notification_utils.js'
|
||||||
import notificationsFetcher from '../../services/notifications_fetcher/notifications_fetcher.service.js'
|
import notificationsFetcher from '../../services/notifications_fetcher/notifications_fetcher.service.js'
|
||||||
import NotificationFilters from './notification_filters.vue'
|
import NotificationFilters from './notification_filters.vue'
|
||||||
|
|
@ -18,6 +17,7 @@ import { useAnnouncementsStore } from 'src/stores/announcements.js'
|
||||||
import { useChatsStore } from 'src/stores/chats.js'
|
import { useChatsStore } from 'src/stores/chats.js'
|
||||||
import { useInterfaceStore } from 'src/stores/interface.js'
|
import { useInterfaceStore } from 'src/stores/interface.js'
|
||||||
import { useMergedConfigStore } from 'src/stores/merged_config.js'
|
import { useMergedConfigStore } from 'src/stores/merged_config.js'
|
||||||
|
import { useNotificationsStore } from 'src/stores/notifications.js'
|
||||||
import { useUsersStore } from 'src/stores/users.js'
|
import { useUsersStore } from 'src/stores/users.js'
|
||||||
|
|
||||||
import { library } from '@fortawesome/fontawesome-svg-core'
|
import { library } from '@fortawesome/fontawesome-svg-core'
|
||||||
|
|
@ -71,14 +71,13 @@ const Notifications = {
|
||||||
return this.minimalMode ? '' : 'panel panel-default'
|
return this.minimalMode ? '' : 'panel panel-default'
|
||||||
},
|
},
|
||||||
notifications() {
|
notifications() {
|
||||||
return notificationsFromStore(this.$store)
|
return useNotificationsStore().data
|
||||||
},
|
},
|
||||||
error() {
|
error() {
|
||||||
return this.$store.state.notifications.error
|
return useNotificationsStore().error
|
||||||
},
|
},
|
||||||
unseenNotifications() {
|
unseenNotifications() {
|
||||||
return unseenNotificationsFromStore(
|
return unseenNotifications(
|
||||||
this.$store,
|
|
||||||
useMergedConfigStore().mergedConfig.notificationVisibility,
|
useMergedConfigStore().mergedConfig.notificationVisibility,
|
||||||
useMergedConfigStore().mergedConfig.ignoreInactionableSeen,
|
useMergedConfigStore().mergedConfig.ignoreInactionableSeen,
|
||||||
)
|
)
|
||||||
|
|
@ -86,18 +85,15 @@ const Notifications = {
|
||||||
filteredNotifications() {
|
filteredNotifications() {
|
||||||
if (this.unseenAtTop) {
|
if (this.unseenAtTop) {
|
||||||
return [
|
return [
|
||||||
...filteredNotificationsFromStore(
|
...filteredNotifications(
|
||||||
this.$store,
|
|
||||||
useMergedConfigStore().mergedConfig.notificationVisibility,
|
useMergedConfigStore().mergedConfig.notificationVisibility,
|
||||||
).filter((n) => this.shouldShowUnseen(n)),
|
).filter((n) => this.shouldShowUnseen(n)),
|
||||||
...filteredNotificationsFromStore(
|
...filteredNotifications(
|
||||||
this.$store,
|
|
||||||
useMergedConfigStore().mergedConfig.notificationVisibility,
|
useMergedConfigStore().mergedConfig.notificationVisibility,
|
||||||
).filter((n) => !this.shouldShowUnseen(n)),
|
).filter((n) => !this.shouldShowUnseen(n)),
|
||||||
]
|
]
|
||||||
} else {
|
} else {
|
||||||
return filteredNotificationsFromStore(
|
return filteredNotifications(
|
||||||
this.$store,
|
|
||||||
useMergedConfigStore().mergedConfig.notificationVisibility,
|
useMergedConfigStore().mergedConfig.notificationVisibility,
|
||||||
this.filterMode,
|
this.filterMode,
|
||||||
)
|
)
|
||||||
|
|
@ -128,7 +124,7 @@ const Notifications = {
|
||||||
)
|
)
|
||||||
},
|
},
|
||||||
loading() {
|
loading() {
|
||||||
return this.$store.state.notifications.loading
|
return useNotificationsStore().loading
|
||||||
},
|
},
|
||||||
noHeading() {
|
noHeading() {
|
||||||
const { layoutType } = useInterfaceStore()
|
const { layoutType } = useInterfaceStore()
|
||||||
|
|
@ -225,14 +221,14 @@ const Notifications = {
|
||||||
*/
|
*/
|
||||||
notificationClicked(notification) {
|
notificationClicked(notification) {
|
||||||
const { id } = notification
|
const { id } = notification
|
||||||
this.$store.dispatch('notificationClicked', { id })
|
useNotificationsStore().notificationClicked(id)
|
||||||
},
|
},
|
||||||
notificationInteracted(notification) {
|
notificationInteracted(notification) {
|
||||||
const { id } = notification
|
const { id } = notification
|
||||||
this.$store.dispatch('markSingleNotificationAsSeen', { id })
|
useNotificationsStore().markSingleNotificationAsSeen(id)
|
||||||
},
|
},
|
||||||
markAsSeen() {
|
markAsSeen() {
|
||||||
this.$store.dispatch('markNotificationsAsSeen')
|
useNotificationsStore().markNotificationsAsSeen()
|
||||||
this.seenToDisplayCount = DEFAULT_SEEN_TO_DISPLAY_COUNT
|
this.seenToDisplayCount = DEFAULT_SEEN_TO_DISPLAY_COUNT
|
||||||
},
|
},
|
||||||
fetchOlderNotifications() {
|
fetchOlderNotifications() {
|
||||||
|
|
@ -253,7 +249,7 @@ const Notifications = {
|
||||||
|
|
||||||
const store = this.$store
|
const store = this.$store
|
||||||
const credentials = useUsersStore().currentUser.credentials
|
const credentials = useUsersStore().currentUser.credentials
|
||||||
store.commit('setNotificationsLoading', { value: true })
|
useNotificationsStore().setNotificationsLoading(true)
|
||||||
notificationsFetcher
|
notificationsFetcher
|
||||||
.fetchAndUpdate({
|
.fetchAndUpdate({
|
||||||
store,
|
store,
|
||||||
|
|
@ -261,7 +257,7 @@ const Notifications = {
|
||||||
older: true,
|
older: true,
|
||||||
})
|
})
|
||||||
.then((notifs) => {
|
.then((notifs) => {
|
||||||
store.commit('setNotificationsLoading', { value: false })
|
useNotificationsStore().setNotificationsLoading(false)
|
||||||
if (notifs.length === 0) {
|
if (notifs.length === 0) {
|
||||||
this.bottomedOut = true
|
this.bottomedOut = true
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -4,7 +4,7 @@ import { mapGetters } from 'vuex'
|
||||||
import { USERNAME_ROUTES } from 'src/components/navigation/navigation.js'
|
import { USERNAME_ROUTES } from 'src/components/navigation/navigation.js'
|
||||||
import UserCard from 'src/components/user_card/user_card.vue'
|
import UserCard from 'src/components/user_card/user_card.vue'
|
||||||
import GestureService from '../../services/gesture_service/gesture_service'
|
import GestureService from '../../services/gesture_service/gesture_service'
|
||||||
import { unseenNotificationsFromStore } from '../../services/notification_utils/notification_utils'
|
import { unseenNotifications } from '../../services/notification_utils/notification_utils'
|
||||||
|
|
||||||
import { useAnnouncementsStore } from 'src/stores/announcements'
|
import { useAnnouncementsStore } from 'src/stores/announcements'
|
||||||
import { useChatsStore } from 'src/stores/chats.js'
|
import { useChatsStore } from 'src/stores/chats.js'
|
||||||
|
|
@ -77,8 +77,7 @@ const SideDrawer = {
|
||||||
return useShoutStore().joined
|
return useShoutStore().joined
|
||||||
},
|
},
|
||||||
unseenNotifications() {
|
unseenNotifications() {
|
||||||
return unseenNotificationsFromStore(
|
return unseenNotifications(
|
||||||
this.$store,
|
|
||||||
useMergedConfigStore().mergedConfig.notificationVisibility,
|
useMergedConfigStore().mergedConfig.notificationVisibility,
|
||||||
useMergedConfigStore().mergedConfig.ignoreInactionableSeen,
|
useMergedConfigStore().mergedConfig.ignoreInactionableSeen,
|
||||||
)
|
)
|
||||||
|
|
|
||||||
|
|
@ -5,6 +5,7 @@ import { maybeShowChatNotification } from '../services/chat_utils/chat_utils.js'
|
||||||
import { useChatsStore } from 'src/stores/chats.js'
|
import { useChatsStore } from 'src/stores/chats.js'
|
||||||
import { useInstanceCapabilitiesStore } from 'src/stores/instance_capabilities.js'
|
import { useInstanceCapabilitiesStore } from 'src/stores/instance_capabilities.js'
|
||||||
import { useInterfaceStore } from 'src/stores/interface.js'
|
import { useInterfaceStore } from 'src/stores/interface.js'
|
||||||
|
import { useNotificationsStore } from 'src/stores/notifications.js'
|
||||||
import { useOAuthStore } from 'src/stores/oauth.js'
|
import { useOAuthStore } from 'src/stores/oauth.js'
|
||||||
import { useShoutStore } from 'src/stores/shout.js'
|
import { useShoutStore } from 'src/stores/shout.js'
|
||||||
|
|
||||||
|
|
@ -117,9 +118,9 @@ const api = {
|
||||||
({ detail: message }) => {
|
({ detail: message }) => {
|
||||||
if (!message) return // pings
|
if (!message) return // pings
|
||||||
if (message.event === 'notification') {
|
if (message.event === 'notification') {
|
||||||
dispatch('addNewNotifications', {
|
useNotificationsStore().addNewNotifications({
|
||||||
notifications: [message.notification],
|
timestamp: Date.now(),
|
||||||
older: false,
|
data: message.notification,
|
||||||
})
|
})
|
||||||
} else if (message.event === 'update') {
|
} else if (message.event === 'update') {
|
||||||
dispatch('addNewStatuses', {
|
dispatch('addNewStatuses', {
|
||||||
|
|
@ -212,7 +213,6 @@ const api = {
|
||||||
if (state.mastoUserSocketStatus !== WSConnectionStatus.ERROR) {
|
if (state.mastoUserSocketStatus !== WSConnectionStatus.ERROR) {
|
||||||
dispatch('startFetchingTimeline', { timeline: 'friends' })
|
dispatch('startFetchingTimeline', { timeline: 'friends' })
|
||||||
dispatch('startFetchingNotifications')
|
dispatch('startFetchingNotifications')
|
||||||
dispatch('startFetchingChats')
|
|
||||||
useInterfaceStore().pushGlobalNotice({
|
useInterfaceStore().pushGlobalNotice({
|
||||||
level: 'error',
|
level: 'error',
|
||||||
messageKey: 'timeline.socket_broke',
|
messageKey: 'timeline.socket_broke',
|
||||||
|
|
@ -234,7 +234,6 @@ const api = {
|
||||||
stopMastoUserSocket({ state, dispatch }) {
|
stopMastoUserSocket({ state, dispatch }) {
|
||||||
dispatch('startFetchingTimeline', { timeline: 'friends' })
|
dispatch('startFetchingTimeline', { timeline: 'friends' })
|
||||||
dispatch('startFetchingNotifications')
|
dispatch('startFetchingNotifications')
|
||||||
dispatch('startFetchingChats')
|
|
||||||
state.mastoUserSocket.close()
|
state.mastoUserSocket.close()
|
||||||
},
|
},
|
||||||
|
|
||||||
|
|
@ -289,7 +288,6 @@ const api = {
|
||||||
startFetchingNotifications(store) {
|
startFetchingNotifications(store) {
|
||||||
if (store.state.fetchers.notifications) return
|
if (store.state.fetchers.notifications) return
|
||||||
const fetcher = notificationsFetcher.startFetching({
|
const fetcher = notificationsFetcher.startFetching({
|
||||||
store,
|
|
||||||
credentials: useOAuthStore().token,
|
credentials: useOAuthStore().token,
|
||||||
})
|
})
|
||||||
store.commit('addFetcher', { fetcherName: 'notifications', fetcher })
|
store.commit('addFetcher', { fetcherName: 'notifications', fetcher })
|
||||||
|
|
|
||||||
|
|
@ -1,12 +1,10 @@
|
||||||
import api from './api.js'
|
import api from './api.js'
|
||||||
import drafts from './drafts.js'
|
import drafts from './drafts.js'
|
||||||
import notifications from './notifications.js'
|
|
||||||
import profileConfig from './profileConfig.js'
|
import profileConfig from './profileConfig.js'
|
||||||
import statuses from './statuses.js'
|
import statuses from './statuses.js'
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
statuses,
|
statuses,
|
||||||
notifications,
|
|
||||||
api,
|
api,
|
||||||
profileConfig,
|
profileConfig,
|
||||||
drafts,
|
drafts,
|
||||||
|
|
|
||||||
|
|
@ -4,14 +4,16 @@ import {
|
||||||
showDesktopNotification as swDesktopNotification,
|
showDesktopNotification as swDesktopNotification,
|
||||||
} from '../sw/sw.js'
|
} from '../sw/sw.js'
|
||||||
|
|
||||||
|
import { useNotificationsStore } from 'src/stores/notifications.js'
|
||||||
|
|
||||||
const state = { failCreateNotif: false }
|
const state = { failCreateNotif: false }
|
||||||
|
|
||||||
export const showDesktopNotification = (rootState, desktopNotificationOpts) => {
|
export const showDesktopNotification = (desktopNotificationOpts) => {
|
||||||
if (
|
if (
|
||||||
!('Notification' in window && window.Notification.permission === 'granted')
|
!('Notification' in window && window.Notification.permission === 'granted')
|
||||||
)
|
)
|
||||||
return
|
return
|
||||||
if (rootState.notifications.desktopNotificationSilence) {
|
if (useNotificationsStore().desktopNotificationSilence) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -30,7 +32,7 @@ export const showDesktopNotification = (rootState, desktopNotificationOpts) => {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export const closeDesktopNotification = (rootState, { id }) => {
|
export const closeDesktopNotification = (id) => {
|
||||||
if (
|
if (
|
||||||
!('Notification' in window && window.Notification.permission === 'granted')
|
!('Notification' in window && window.Notification.permission === 'granted')
|
||||||
)
|
)
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,8 @@
|
||||||
import { showDesktopNotification } from '../desktop_notification_utils/desktop_notification_utils.js'
|
import { showDesktopNotification } from '../desktop_notification_utils/desktop_notification_utils.js'
|
||||||
import { muteFilterHits } from '../status_parser/status_parser.js'
|
import { muteFilterHits } from '../status_parser/status_parser.js'
|
||||||
|
|
||||||
|
import { useNotificationsStore } from 'src/stores/notifications.js'
|
||||||
|
|
||||||
import FaviconService from 'src/services/favicon_service/favicon_service.js'
|
import FaviconService from 'src/services/favicon_service/favicon_service.js'
|
||||||
|
|
||||||
export const ACTIONABLE_NOTIFICATION_TYPES = new Set([
|
export const ACTIONABLE_NOTIFICATION_TYPES = new Set([
|
||||||
|
|
@ -11,8 +13,6 @@ export const ACTIONABLE_NOTIFICATION_TYPES = new Set([
|
||||||
|
|
||||||
let cachedBadgeUrl = null
|
let cachedBadgeUrl = null
|
||||||
|
|
||||||
export const notificationsFromStore = (store) => store.state.notifications.data
|
|
||||||
|
|
||||||
const visibleTypes = (notificationVisibility) => {
|
const visibleTypes = (notificationVisibility) => {
|
||||||
return [
|
return [
|
||||||
notificationVisibility.likes && 'like',
|
notificationVisibility.likes && 'like',
|
||||||
|
|
@ -69,14 +69,11 @@ const isMutedNotification = (muteFilters, notification) => {
|
||||||
}
|
}
|
||||||
|
|
||||||
export const maybeShowNotification = (
|
export const maybeShowNotification = (
|
||||||
store,
|
|
||||||
notificationVisibility,
|
notificationVisibility,
|
||||||
muteFilters,
|
muteFilters,
|
||||||
notification,
|
notification,
|
||||||
i18n,
|
i18n,
|
||||||
) => {
|
) => {
|
||||||
const rootState = store.rootState || store.state
|
|
||||||
|
|
||||||
if (notification.seen) return
|
if (notification.seen) return
|
||||||
if (!visibleTypes(notificationVisibility).includes(notification.type)) return
|
if (!visibleTypes(notificationVisibility).includes(notification.type)) return
|
||||||
if (
|
if (
|
||||||
|
|
@ -86,28 +83,23 @@ export const maybeShowNotification = (
|
||||||
return
|
return
|
||||||
|
|
||||||
const notificationObject = prepareNotificationObject(notification, i18n)
|
const notificationObject = prepareNotificationObject(notification, i18n)
|
||||||
showDesktopNotification(rootState, notificationObject)
|
showDesktopNotification(notificationObject)
|
||||||
}
|
}
|
||||||
|
|
||||||
export const filteredNotificationsFromStore = (
|
export const filteredNotifications = (notificationVisibility, types) => {
|
||||||
store,
|
|
||||||
notificationVisibility,
|
|
||||||
types,
|
|
||||||
) => {
|
|
||||||
// map is just to clone the array since sort mutates it and it causes some issues
|
// map is just to clone the array since sort mutates it and it causes some issues
|
||||||
const sortedNotifications = notificationsFromStore(store).sort(sortById)
|
const sortedNotifications = useNotificationsStore().data.sort(sortById)
|
||||||
// TODO implement sorting elsewhere and make it optional
|
// TODO implement sorting elsewhere and make it optional
|
||||||
return sortedNotifications.filter((notification) =>
|
return sortedNotifications.filter((notification) =>
|
||||||
(types || visibleTypes(notificationVisibility)).includes(notification.type),
|
(types || visibleTypes(notificationVisibility)).includes(notification.type),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
export const unseenNotificationsFromStore = (
|
export const unseenNotifications = (
|
||||||
store,
|
|
||||||
notificationVisibility,
|
notificationVisibility,
|
||||||
ignoreInactionableSeen,
|
ignoreInactionableSeen,
|
||||||
) => {
|
) => {
|
||||||
return filteredNotificationsFromStore(store, notificationVisibility).filter(
|
return filteredNotifications(notificationVisibility).filter(
|
||||||
({ seen, type }) => {
|
({ seen, type }) => {
|
||||||
if (!ignoreInactionableSeen) return !seen
|
if (!ignoreInactionableSeen) return !seen
|
||||||
if (seen) return false
|
if (seen) return false
|
||||||
|
|
|
||||||
|
|
@ -3,12 +3,10 @@ import { promiseInterval } from '../promise_interval/promise_interval.js'
|
||||||
import { useInstanceCapabilitiesStore } from 'src/stores/instance_capabilities.js'
|
import { useInstanceCapabilitiesStore } from 'src/stores/instance_capabilities.js'
|
||||||
import { useInterfaceStore } from 'src/stores/interface.js'
|
import { useInterfaceStore } from 'src/stores/interface.js'
|
||||||
import { useMergedConfigStore } from 'src/stores/merged_config.js'
|
import { useMergedConfigStore } from 'src/stores/merged_config.js'
|
||||||
|
import { useNotificationsStore } from 'src/stores/notifications.js'
|
||||||
|
|
||||||
import { fetchTimeline } from 'src/api/timelines.js'
|
import { fetchTimeline } from 'src/api/timelines.js'
|
||||||
|
|
||||||
const update = ({ store, notifications, older }) => {
|
|
||||||
store.dispatch('addNewNotifications', { notifications, older })
|
|
||||||
}
|
|
||||||
//
|
//
|
||||||
// For using include_types when fetching notifications.
|
// For using include_types when fetching notifications.
|
||||||
// Note: chat_mention excluded as pleroma-fe polls them separately
|
// Note: chat_mention excluded as pleroma-fe polls them separately
|
||||||
|
|
@ -25,10 +23,9 @@ const mastoApiNotificationTypes = new Set([
|
||||||
'pleroma:report',
|
'pleroma:report',
|
||||||
])
|
])
|
||||||
|
|
||||||
const fetchAndUpdate = ({ store, credentials, older = false, sinceId }) => {
|
const fetchAndUpdate = ({ credentials, older = false, sinceId }) => {
|
||||||
const args = { credentials }
|
const args = { credentials }
|
||||||
const rootState = store.rootState || store.state
|
const timelineData = useNotificationsStore()
|
||||||
const timelineData = rootState.notifications
|
|
||||||
const hideMutedPosts = useMergedConfigStore().mergedConfig.hideMutedPosts
|
const hideMutedPosts = useMergedConfigStore().mergedConfig.hideMutedPosts
|
||||||
|
|
||||||
if (useInstanceCapabilitiesStore().pleromaChatMessagesAvailable) {
|
if (useInstanceCapabilitiesStore().pleromaChatMessagesAvailable) {
|
||||||
|
|
@ -43,7 +40,7 @@ const fetchAndUpdate = ({ store, credentials, older = false, sinceId }) => {
|
||||||
if (timelineData.minId !== Number.POSITIVE_INFINITY) {
|
if (timelineData.minId !== Number.POSITIVE_INFINITY) {
|
||||||
args.maxId = timelineData.minId
|
args.maxId = timelineData.minId
|
||||||
}
|
}
|
||||||
return fetchNotifications({ store, args, older })
|
return fetchNotifications({ args, older })
|
||||||
} else {
|
} else {
|
||||||
// fetch new notifications
|
// fetch new notifications
|
||||||
if (
|
if (
|
||||||
|
|
@ -54,7 +51,7 @@ const fetchAndUpdate = ({ store, credentials, older = false, sinceId }) => {
|
||||||
} else if (sinceId !== null) {
|
} else if (sinceId !== null) {
|
||||||
args.sinceId = sinceId
|
args.sinceId = sinceId
|
||||||
}
|
}
|
||||||
const result = fetchNotifications({ store, args, older })
|
const result = fetchNotifications({ args, older })
|
||||||
|
|
||||||
// If there's any unread notifications, try fetch notifications since
|
// If there's any unread notifications, try fetch notifications since
|
||||||
// the newest read notification to check if any of the unread notifs
|
// the newest read notification to check if any of the unread notifs
|
||||||
|
|
@ -72,7 +69,7 @@ const fetchAndUpdate = ({ store, credentials, older = false, sinceId }) => {
|
||||||
if (minId !== Infinity) {
|
if (minId !== Infinity) {
|
||||||
args.sinceId = null // Don't use since_id since it sorta conflicts with min_id
|
args.sinceId = null // Don't use since_id since it sorta conflicts with min_id
|
||||||
args.minId = minId - 1 // go beyond
|
args.minId = minId - 1 // go beyond
|
||||||
fetchNotifications({ store, args, older })
|
fetchNotifications({ args, older })
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -80,11 +77,13 @@ const fetchAndUpdate = ({ store, credentials, older = false, sinceId }) => {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const fetchNotifications = ({ store, args, older }) => {
|
const fetchNotifications = ({ args, older }) => {
|
||||||
return fetchTimeline(args)
|
return fetchTimeline(args)
|
||||||
.then((response) => {
|
.then((response) => {
|
||||||
const notifications = response.data
|
const notifications = response.data
|
||||||
update({ store, notifications, older })
|
|
||||||
|
useNotificationsStore().addNewNotifications(response)
|
||||||
|
|
||||||
return notifications
|
return notifications
|
||||||
})
|
})
|
||||||
.catch((error) => {
|
.catch((error) => {
|
||||||
|
|
@ -97,7 +96,7 @@ const fetchNotifications = ({ store, args, older }) => {
|
||||||
.toArray()
|
.toArray()
|
||||||
.map((x) => x[1])
|
.map((x) => x[1])
|
||||||
.forEach((x) => mastoApiNotificationTypes.delete(x))
|
.forEach((x) => mastoApiNotificationTypes.delete(x))
|
||||||
return fetchNotifications({ store, args, older })
|
return fetchNotifications({ args, older })
|
||||||
}
|
}
|
||||||
|
|
||||||
useInterfaceStore().pushGlobalNotice({
|
useInterfaceStore().pushGlobalNotice({
|
||||||
|
|
@ -114,7 +113,7 @@ const startFetching = ({ credentials, store }) => {
|
||||||
// Initially there's set flag to silence all desktop notifications so
|
// Initially there's set flag to silence all desktop notifications so
|
||||||
// that there won't spam of them when user just opened up the FE we
|
// that there won't spam of them when user just opened up the FE we
|
||||||
// reset that flag after a while to show new notifications once again.
|
// reset that flag after a while to show new notifications once again.
|
||||||
setTimeout(() => store.dispatch('setNotificationsSilence', false), 10000)
|
setTimeout(() => useNotificationsStore().setNotificationsSilence(false), 10000)
|
||||||
const boundFetchAndUpdate = () => fetchAndUpdate({ credentials, store })
|
const boundFetchAndUpdate = () => fetchAndUpdate({ credentials, store })
|
||||||
boundFetchAndUpdate()
|
boundFetchAndUpdate()
|
||||||
return promiseInterval(boundFetchAndUpdate, 10000)
|
return promiseInterval(boundFetchAndUpdate, 10000)
|
||||||
|
|
|
||||||
|
|
@ -1,3 +1,5 @@
|
||||||
|
import { defineStore } from 'pinia'
|
||||||
|
|
||||||
import {
|
import {
|
||||||
closeAllDesktopNotifications,
|
closeAllDesktopNotifications,
|
||||||
closeDesktopNotification,
|
closeDesktopNotification,
|
||||||
|
|
@ -17,70 +19,56 @@ import { useUsersStore } from 'src/stores/users.js'
|
||||||
|
|
||||||
import { dismissNotification, markNotificationsAsSeen } from 'src/api/user.js'
|
import { dismissNotification, markNotificationsAsSeen } from 'src/api/user.js'
|
||||||
|
|
||||||
const emptyNotifications = () => ({
|
export const defaultState = () => ({
|
||||||
desktopNotificationSilence: true,
|
desktopNotificationSilence: true,
|
||||||
maxId: 0,
|
maxId: 0,
|
||||||
minId: Number.POSITIVE_INFINITY,
|
minId: Number.POSITIVE_INFINITY,
|
||||||
data: [],
|
data: [],
|
||||||
idStore: {},
|
statusNotificationRelations: new WeakMap(),
|
||||||
|
idStore: new Map(),
|
||||||
loading: false,
|
loading: false,
|
||||||
})
|
})
|
||||||
|
|
||||||
export const defaultState = () => ({
|
export const useNotificationsStore = defineStore('notifications', {
|
||||||
...emptyNotifications(),
|
state: defaultState,
|
||||||
})
|
actions: {
|
||||||
|
clearNotifications() {
|
||||||
export const notifications = {
|
|
||||||
state: defaultState(),
|
|
||||||
mutations: {
|
|
||||||
addNewNotifications(state, { notifications }) {
|
|
||||||
notifications.forEach((notification) => {
|
|
||||||
state.data.push(notification)
|
|
||||||
state.idStore[notification.id] = notification
|
|
||||||
})
|
|
||||||
},
|
|
||||||
clearNotifications(state) {
|
|
||||||
const blankState = defaultState()
|
const blankState = defaultState()
|
||||||
Object.keys(state).forEach((k) => {
|
|
||||||
state[k] = blankState[k]
|
Object.keys(defaultState()).forEach((k) => {
|
||||||
|
this[k] = blankState[k]
|
||||||
})
|
})
|
||||||
},
|
},
|
||||||
updateNotificationsMinMaxId(state, id) {
|
updateNotificationsMinMaxId(id) {
|
||||||
state.maxId = id > state.maxId ? id : state.maxId
|
this.maxId = id > this.maxId ? id : this.maxId
|
||||||
state.minId = id < state.minId ? id : state.minId
|
this.minId = id < this.minId ? id : this.minId
|
||||||
},
|
},
|
||||||
setNotificationsLoading(state, { value }) {
|
setNotificationsLoading(value) {
|
||||||
state.loading = value
|
this.loading = value
|
||||||
},
|
},
|
||||||
setNotificationsSilence(state, { value }) {
|
setNotificationsSilence(value) {
|
||||||
state.desktopNotificationSilence = value
|
this.desktopNotificationSilence = value
|
||||||
},
|
},
|
||||||
markNotificationsAsSeen(state) {
|
updateNotification({ id, updater }) {
|
||||||
state.data.forEach((notification) => {
|
const notification = this.idStore.get(id)
|
||||||
notification.seen = true
|
|
||||||
})
|
|
||||||
},
|
|
||||||
markSingleNotificationAsSeen(state, { id }) {
|
|
||||||
const notification = state.idStore[id]
|
|
||||||
if (notification) notification.seen = true
|
|
||||||
},
|
|
||||||
dismissNotification(state, { id }) {
|
|
||||||
state.data = state.data.filter((n) => n.id !== id)
|
|
||||||
delete state.idStore[id]
|
|
||||||
},
|
|
||||||
updateNotification(state, { id, updater }) {
|
|
||||||
const notification = state.idStore[id]
|
|
||||||
notification && updater(notification)
|
notification && updater(notification)
|
||||||
},
|
},
|
||||||
},
|
addNewNotifications(result) {
|
||||||
actions: {
|
const { timestamp, data: notifications } = result
|
||||||
addNewNotifications(store, { notifications }) {
|
|
||||||
const { commit, dispatch, state, rootState } = store
|
useUsersStore().addNewUsers({
|
||||||
|
timestamp,
|
||||||
|
data: notifications.map((n) => n.from_profile),
|
||||||
|
})
|
||||||
|
notifications.forEach(
|
||||||
|
(n) => (n.from_profile = useUsersStore().findUser(n.from_profile.id)),
|
||||||
|
)
|
||||||
|
|
||||||
const validNotifications = notifications.filter((notification) => {
|
const validNotifications = notifications.filter((notification) => {
|
||||||
// If invalid notification, update ids but don't add it to store
|
// If invalid notification, update ids but don't add it to store
|
||||||
if (!isValidNotification(notification)) {
|
if (!isValidNotification(notification)) {
|
||||||
console.error('Invalid notification:', notification)
|
console.error('Invalid notification:', notification)
|
||||||
commit('updateNotificationsMinMaxId', notification.id)
|
this.updateNotificationsMinMaxId(notification.id)
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
return true
|
return true
|
||||||
|
|
@ -92,7 +80,8 @@ export const notifications = {
|
||||||
)
|
)
|
||||||
|
|
||||||
// Synchronous commit to add all the statuses
|
// Synchronous commit to add all the statuses
|
||||||
commit('addNewStatuses', {
|
window.vuex.commit('addNewStatuses', {
|
||||||
|
timestamp,
|
||||||
statuses: statusNotifications.map(
|
statuses: statusNotifications.map(
|
||||||
(notification) => notification.status,
|
(notification) => notification.status,
|
||||||
),
|
),
|
||||||
|
|
@ -101,7 +90,7 @@ export const notifications = {
|
||||||
// Update references to statuses in notifications to ones in the store
|
// Update references to statuses in notifications to ones in the store
|
||||||
statusNotifications.forEach((notification) => {
|
statusNotifications.forEach((notification) => {
|
||||||
const id = notification.status.id
|
const id = notification.status.id
|
||||||
const referenceStatus = rootState.statuses.allStatusesObject[id]
|
const referenceStatus = window.vuex.state.statuses.allStatusesObject[id]
|
||||||
|
|
||||||
if (referenceStatus) {
|
if (referenceStatus) {
|
||||||
notification.status = referenceStatus
|
notification.status = referenceStatus
|
||||||
|
|
@ -114,28 +103,36 @@ export const notifications = {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (notification.type === 'pleroma:emoji_reaction') {
|
if (notification.type === 'pleroma:emoji_reaction') {
|
||||||
dispatch('fetchEmojiReactionsBy', notification.status.id)
|
window.vuex.dispatch('fetchEmojiReactionsBy', notification.status.id)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Only add a new notification if we don't have one for the same action
|
// Only add a new notification if we don't have one for the same action
|
||||||
if (!Object.hasOwn(state.idStore, notification.id)) {
|
if (!this.idStore.has(notification.id)) {
|
||||||
commit('updateNotificationsMinMaxId', notification.id)
|
this.updateNotificationsMinMaxId(notification.id)
|
||||||
commit('addNewNotifications', { notifications: [notification] })
|
|
||||||
|
notifications.forEach((notification) => {
|
||||||
|
this.data.push(notification)
|
||||||
|
this.idStore.set(notification.id, notification)
|
||||||
|
})
|
||||||
|
|
||||||
|
this.statusNotificationRelations.set(
|
||||||
|
notification.status,
|
||||||
|
this.idStore.get(notification.id),
|
||||||
|
)
|
||||||
|
|
||||||
maybeShowNotification(
|
maybeShowNotification(
|
||||||
store,
|
|
||||||
useMergedConfigStore().mergedConfig.notificationVisibility,
|
useMergedConfigStore().mergedConfig.notificationVisibility,
|
||||||
Object.values(useSyncConfigStore().prefsStorage.simple.muteFilters),
|
Object.values(useSyncConfigStore().prefsStorage.simple.muteFilters),
|
||||||
notification,
|
notification,
|
||||||
useI18nStore().i18n,
|
useI18nStore().i18n,
|
||||||
)
|
)
|
||||||
} else if (notification.seen) {
|
} else if (notification.seen) {
|
||||||
state.idStore[notification.id].seen = true
|
this.idStore.get(notification.id).seen = true
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
},
|
},
|
||||||
notificationClicked({ state, dispatch }, { id }) {
|
notificationClicked(id) {
|
||||||
const notification = state.idStore[id]
|
const notification = this.idStore.get(id)
|
||||||
const { type, seen } = notification
|
const { type, seen } = notification
|
||||||
|
|
||||||
if (!seen) {
|
if (!seen) {
|
||||||
|
|
@ -145,49 +142,45 @@ export const notifications = {
|
||||||
case 'follow_request':
|
case 'follow_request':
|
||||||
break
|
break
|
||||||
default:
|
default:
|
||||||
dispatch('markSingleNotificationAsSeen', { id })
|
this.markSingleNotificationAsSeen({ id })
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
setNotificationsLoading({ commit }, { value }) {
|
markNotificationsAsSeen() {
|
||||||
commit('setNotificationsLoading', { value })
|
this.data.forEach((notification) => {
|
||||||
},
|
notification.seen = true
|
||||||
setNotificationsSilence({ commit }, { value }) {
|
})
|
||||||
commit('setNotificationsSilence', { value })
|
|
||||||
},
|
|
||||||
markNotificationsAsSeen({ rootState, state, commit }) {
|
|
||||||
commit('markNotificationsAsSeen')
|
|
||||||
markNotificationsAsSeen({
|
markNotificationsAsSeen({
|
||||||
id: state.maxId,
|
id: this.maxId,
|
||||||
credentials: useUsersStore().currentUser.credentials,
|
credentials: useUsersStore().currentUser.credentials,
|
||||||
}).then(() => {
|
}).then(() => {
|
||||||
closeAllDesktopNotifications(rootState)
|
closeAllDesktopNotifications()
|
||||||
})
|
})
|
||||||
},
|
},
|
||||||
markSingleNotificationAsSeen({ rootState, commit }, { id }) {
|
markSingleNotificationAsSeen({ id }) {
|
||||||
commit('markSingleNotificationAsSeen', { id })
|
const notification = this.idStore.get(id)
|
||||||
|
if (notification) notification.seen = true
|
||||||
|
|
||||||
markNotificationsAsSeen({
|
markNotificationsAsSeen({
|
||||||
single: true,
|
single: true,
|
||||||
id,
|
id,
|
||||||
credentials: useUsersStore().currentUser.credentials,
|
credentials: useUsersStore().currentUser.credentials,
|
||||||
}).then(() => {
|
}).then(() => {
|
||||||
closeDesktopNotification(rootState, { id })
|
closeDesktopNotification(id)
|
||||||
})
|
})
|
||||||
},
|
},
|
||||||
dismissNotificationLocal({ commit }, { id }) {
|
dismissNotificationLocal(id) {
|
||||||
commit('dismissNotification', { id })
|
this.data = this.data.filter((n) => n.id !== id)
|
||||||
|
delete this.idStore.delete(id)
|
||||||
},
|
},
|
||||||
dismissNotification({ rootState, commit }, { id }) {
|
dismissNotification(id) {
|
||||||
commit('dismissNotification', { id })
|
this.dismissNotificationLocal(id)
|
||||||
|
|
||||||
dismissNotification({
|
dismissNotification({
|
||||||
id,
|
id,
|
||||||
credentials: useOAuthStore().token,
|
credentials: useOAuthStore().token,
|
||||||
})
|
})
|
||||||
},
|
},
|
||||||
updateNotification({ commit }, { id, updater }) {
|
|
||||||
commit('updateNotification', { id, updater })
|
|
||||||
},
|
|
||||||
},
|
},
|
||||||
}
|
})
|
||||||
|
|
||||||
export default notifications
|
|
||||||
|
|
@ -697,7 +697,7 @@ export const useUsersStore = defineStore('users', {
|
||||||
.then(() => {
|
.then(() => {
|
||||||
dispatch('fetchChats', { latest: true })
|
dispatch('fetchChats', { latest: true })
|
||||||
setTimeout(
|
setTimeout(
|
||||||
() => dispatch('setNotificationsSilence', false),
|
() => useNotificationsStore().setNotificationsSilence(false),
|
||||||
10000,
|
10000,
|
||||||
)
|
)
|
||||||
})
|
})
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue