diff options
author | Antreesy <antreesy.web@gmail.com> | 2023-04-21 21:22:02 +0200 |
---|---|---|
committer | Antreesy <antreesy.web@gmail.com> | 2023-04-21 21:22:02 +0200 |
commit | 041e3e5c26db6a75684d3720467428142a6b9fe7 (patch) | |
tree | 7096260f20802f4dabea7fd17e1728ee09a3c6c3 | |
parent | e6629b1dcfca8204af30751bfb396c30ff41a824 (diff) |
Add conditional button for marking conversation as read / unread, connect API
Signed-off-by: Antreesy <antreesy.web@gmail.com>
-rw-r--r-- | src/components/LeftSidebar/ConversationsList/Conversation.spec.js | 12 | ||||
-rw-r--r-- | src/components/LeftSidebar/ConversationsList/Conversation.vue | 24 | ||||
-rw-r--r-- | src/services/conversationsService.js | 15 | ||||
-rw-r--r-- | src/store/conversationsStore.js | 23 | ||||
-rw-r--r-- | src/store/conversationsStore.spec.js | 28 |
5 files changed, 92 insertions, 10 deletions
diff --git a/src/components/LeftSidebar/ConversationsList/Conversation.spec.js b/src/components/LeftSidebar/ConversationsList/Conversation.spec.js index a6434108e..5a6ab3ad4 100644 --- a/src/components/LeftSidebar/ConversationsList/Conversation.spec.js +++ b/src/components/LeftSidebar/ConversationsList/Conversation.spec.js @@ -530,10 +530,22 @@ describe('Conversation.vue', () => { expect(toggleFavoriteAction).toHaveBeenCalledWith(expect.anything(), item) }) + test('marks conversation as unread', async () => { + const markConversationUnreadAction = jest.fn().mockResolvedValueOnce() + testStoreConfig.modules.conversationsStore.actions.markConversationUnread = markConversationUnreadAction + + const action = shallowMountAndGetAction('Mark as unread') + expect(action.exists()).toBe(true) + + await action.find('button').trigger('click') + + expect(markConversationUnreadAction).toHaveBeenCalledWith(expect.anything(), { token: item.token }) + }) test('marks conversation as read', async () => { const clearLastReadMessageAction = jest.fn().mockResolvedValueOnce() testStoreConfig.modules.conversationsStore.actions.clearLastReadMessage = clearLastReadMessageAction + item.unreadMessages = 1 const action = shallowMountAndGetAction('Mark as read') expect(action.exists()).toBe(true) diff --git a/src/components/LeftSidebar/ConversationsList/Conversation.vue b/src/components/LeftSidebar/ConversationsList/Conversation.vue index 94224fd84..1376e4997 100644 --- a/src/components/LeftSidebar/ConversationsList/Conversation.vue +++ b/src/components/LeftSidebar/ConversationsList/Conversation.vue @@ -62,13 +62,22 @@ @click.stop.prevent="handleCopyLink"> {{ t('spreed', 'Copy link') }} </NcActionButton> - <NcActionButton :close-after-click="true" + <NcActionButton v-if="item.unreadMessages" + :close-after-click="true" @click.prevent.exact="markConversationAsRead"> <template #icon> <EyeOutline :size="16" /> </template> {{ t('spreed', 'Mark as read') }} </NcActionButton> + <NcActionButton v-else + :close-after-click="true" + @click.prevent.exact="markConversationAsUnread"> + <template #icon> + <EyeOffOutline :size="16" /> + </template> + {{ t('spreed', 'Mark as unread') }} + </NcActionButton> <NcActionButton :close-after-click="true" @click.prevent.exact="showConversationSettings"> <Cog slot="icon" @@ -116,6 +125,7 @@ import ArrowRight from 'vue-material-design-icons/ArrowRight.vue' import Cog from 'vue-material-design-icons/Cog.vue' import Delete from 'vue-material-design-icons/Delete.vue' import ExitToApp from 'vue-material-design-icons/ExitToApp.vue' +import EyeOffOutline from 'vue-material-design-icons/EyeOffOutline.vue' import EyeOutline from 'vue-material-design-icons/EyeOutline.vue' import Star from 'vue-material-design-icons/Star.vue' @@ -134,14 +144,16 @@ export default { name: 'Conversation', components: { + ConversationIcon, + NcActionButton, + NcListItem, + // Icons ArrowRight, Cog, - ConversationIcon, Delete, ExitToApp, + EyeOffOutline, EyeOutline, - NcActionButton, - NcListItem, Star, }, @@ -350,6 +362,10 @@ export default { this.$store.dispatch('clearLastReadMessage', { token: this.item.token }) }, + markConversationAsUnread() { + this.$store.dispatch('markConversationUnread', { token: this.item.token }) + }, + showConversationSettings() { emit('show-conversation-settings', { token: this.item.token }) }, diff --git a/src/services/conversationsService.js b/src/services/conversationsService.js index 12c754aaf..05547a5a0 100644 --- a/src/services/conversationsService.js +++ b/src/services/conversationsService.js @@ -207,6 +207,20 @@ const clearConversationHistory = async function(token) { } /** + * Set conversation as unread + * + * @param {string} token The token of the conversation to be set as unread + */ +const setConversationUnread = async function(token) { + try { + const response = axios.delete(generateOcsUrl('apps/spreed/api/v1/chat/{token}/read', { token })) + return response + } catch (error) { + console.debug('Error while setting the conversation as unread: ', error) + } +} + +/** * Add a conversation to the favorites * * @param {string} token The token of the conversation to be favorites @@ -441,6 +455,7 @@ export { setConversationName, setConversationDescription, clearConversationHistory, + setConversationUnread, setConversationPermissions, setCallPermissions, setMessageExpiration, diff --git a/src/store/conversationsStore.js b/src/store/conversationsStore.js index 69c199232..68f96b661 100644 --- a/src/store/conversationsStore.js +++ b/src/store/conversationsStore.js @@ -46,6 +46,7 @@ import { setConversationDescription, deleteConversation, clearConversationHistory, + setConversationUnread, setNotificationLevel, setNotificationCalls, setConversationPermissions, @@ -129,7 +130,7 @@ const mutations = { Vue.delete(state.conversations, token) }, /** - * Resets the store to it's original state + * Resets the store to its original state * * @param {object} state current store state; */ @@ -428,15 +429,25 @@ const actions = { }, async markConversationRead({ commit, getters }, token) { - const conversation = Object.assign({}, getters.conversations[token]) - if (!conversation) { + if (!getters.conversations[token]) { return } - conversation.unreadMessages = 0 - conversation.unreadMention = false + commit('updateUnreadMessages', { token, unreadMessages: 0, unreadMention: false }) + }, - commit('addConversation', conversation) + async markConversationUnread({ commit, dispatch, getters }, { token }) { + if (!getters.conversations[token]) { + return + } + + try { + await setConversationUnread(token) + commit('updateUnreadMessages', { token, unreadMessages: 1 }) + await dispatch('fetchConversation', { token }) + } catch (error) { + console.debug('Error while marking conversation as unread: ', error) + } }, async updateLastCommonReadMessage({ commit, getters }, { token, lastCommonReadMessage }) { diff --git a/src/store/conversationsStore.spec.js b/src/store/conversationsStore.spec.js index 741fd6c6f..54a7ecde2 100644 --- a/src/store/conversationsStore.spec.js +++ b/src/store/conversationsStore.spec.js @@ -1,4 +1,5 @@ import { createLocalVue } from '@vue/test-utils' +import flushPromises from 'flush-promises' import { cloneDeep } from 'lodash' import Vuex from 'vuex' @@ -26,6 +27,7 @@ import { deleteConversation, setConversationPermissions, setCallPermissions, + setConversationUnread, } from '../services/conversationsService.js' import storeConfig from './storeConfig.js' @@ -47,6 +49,7 @@ jest.mock('../services/conversationsService', () => ({ deleteConversation: jest.fn(), setConversationPermissions: jest.fn(), setCallPermissions: jest.fn(), + setConversationUnread: jest.fn(), })) describe('conversationsStore', () => { @@ -583,6 +586,31 @@ describe('conversationsStore', () => { expect(changedConversation.unreadMention).toBe(false) }) + test('marks conversation as unread', async () => { + testConversation.unreadMessages = 0 + + const response = { + data: { + ocs: { + data: { ...testConversation, unreadMessages: 1 }, + }, + }, + } + fetchConversation.mockResolvedValue(response) + + store.dispatch('addConversation', testConversation) + + store.dispatch('markConversationUnread', { token: testToken }) + + await flushPromises() + + expect(setConversationUnread).toHaveBeenCalled() + expect(fetchConversation).toHaveBeenCalled() + + const changedConversation = store.getters.conversation(testToken) + expect(changedConversation.unreadMessages).toBe(1) + }) + test('updates last common read message', () => { testConversation.lastCommonReadMessage = { id: 999, |