Mark notifications as read based on call to action (#14439)

This commit is contained in:
Icaro Motta 2022-11-25 16:10:29 -03:00 committed by GitHub
parent 3d71fdba98
commit 42de2a6384
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 159 additions and 40 deletions

View File

@ -6,6 +6,14 @@
[status-im.utils.fx :as fx]
[taoensso.timbre :as log]))
(def defaults
{:filter-status :unread
:filter-type types/no-type
;; Choose the maximum number of notifications that *usually/safely* fit on
;; most screens, so that the UI doesn't have to needlessly render
;; notifications.
:notifications-per-page 8})
;;;; Navigation
(fx/defn open-activity-center
@ -75,6 +83,35 @@
(map data-store.activities/<-rpc)
(notifications-reconcile cofx)))
;;;; Mark notifications as read
(defn- get-notification
[db notification-id]
(->> (get-in db [:activity-center
:notifications
(get-in db [:activity-center :filter :type])
(get-in db [:activity-center :filter :status])
:data])
(filter #(= notification-id (:id %)))
first))
(fx/defn mark-as-read
{:events [:activity-center.notifications/mark-as-read]}
[{:keys [db]} notification-id]
(when-let [notification (get-notification db notification-id)]
{::json-rpc/call [{:method "wakuext_markActivityCenterNotificationsRead"
:params [[notification-id]]
:on-success #(rf/dispatch [:activity-center.notifications/mark-as-read-success notification])
:on-error #(rf/dispatch [:activity-center/process-notification-failure
notification-id
:notification/mark-as-read
%])}]}))
(fx/defn mark-as-read-success
{:events [:activity-center.notifications/mark-as-read-success]}
[cofx notification]
(notifications-reconcile cofx [(assoc notification :read true)]))
;;;; Contact verification
(fx/defn contact-verification-decline
@ -123,14 +160,6 @@
;;;; Notifications fetching and pagination
(def defaults
{:filter-status :unread
:filter-type types/no-type
;; Choose the maximum number of notifications that *usually/safely* fit on
;; most screens, so that the UI doesn't have to needlessly render
;; notifications.
:notifications-per-page 8})
(def start-or-end-cursor
"")

View File

@ -9,13 +9,105 @@
[status-im.test-helpers :as h]
[status-im2.setup.config :as config]))
(def notification-id "0x1")
(defn setup []
(h/register-helper-events)
(rf/dispatch [:setup/app-started]))
;;;; Contact verification
(defn test-log-on-failure
[{:keys [before-test notification-id event action]}]
(rf-test/run-test-sync
(setup)
(h/using-log-test-appender
(fn [logs]
(when before-test
(before-test))
(h/stub-fx-with-callbacks ::json-rpc/call :on-error (constantly :fake-error))
(def notification-id 24)
(rf/dispatch event)
(is (= {:args [(str "Failed to " action)
{:notification-id notification-id
:error :fake-error}]
:level :warn}
(last @logs)))))))
;;;; Misc
(deftest mark-as-read-test
(testing "does nothing if the notification ID cannot be found in the app db"
(rf-test/run-test-sync
(setup)
(let [spy-queue (atom [])]
(h/spy-fx spy-queue ::json-rpc/call)
(let [notifications {types/one-to-one-chat
{:all {:cursor "" :data [{:id notification-id
:read false
:type types/one-to-one-chat}]}
:unread {:cursor "" :data []}}}]
(rf/dispatch [:test/assoc-in [:activity-center]
{:notifications notifications
:filter {:type types/one-to-one-chat
:status :all}}])
(rf/dispatch [:activity-center.notifications/mark-as-read "0x666"])
(is (= [] @spy-queue))
(is (= notifications (get-in (h/db) [:activity-center :notifications])))))))
(testing "marks notifications as read and updates app db"
(rf-test/run-test-sync
(setup)
(let [notif-1 {:id "0x1" :read true :type types/one-to-one-chat}
notif-2 {:id "0x2" :read false :type types/one-to-one-chat}
notif-3 {:id "0x3" :read false :type types/one-to-one-chat}
new-notif-3 (assoc notif-3 :read true)
new-notif-2 (assoc notif-2 :read true)]
(h/stub-fx-with-callbacks ::json-rpc/call :on-success (constantly nil))
(rf/dispatch [:test/assoc-in [:activity-center]
{:notifications {types/one-to-one-chat
{:all {:cursor "" :data [notif-3 notif-2 notif-1]}
:unread {:cursor "" :data [notif-3 notif-2]}}}
:filter {:type types/one-to-one-chat
:status :unread}}])
(rf/dispatch [:activity-center.notifications/mark-as-read (:id notif-2)])
(is (= {types/one-to-one-chat
{:all {:cursor "" :data [notif-3 new-notif-2 notif-1]}
:unread {:cursor "" :data [notif-3]}}
types/no-type
{:all {:data [new-notif-2]}
:unread {:data []}}}
(get-in (h/db) [:activity-center :notifications])))
(rf/dispatch [:activity-center.notifications/mark-as-read (:id notif-3)])
(is (= {types/one-to-one-chat
{:all {:cursor "" :data [new-notif-3 new-notif-2 notif-1]}
:unread {:cursor "" :data []}}
types/no-type
{:all {:data [new-notif-3 new-notif-2]}
:unread {:data []}}}
(get-in (h/db) [:activity-center :notifications]))))))
(testing "logs on failure"
(test-log-on-failure
{:notification-id notification-id
:event [:activity-center.notifications/mark-as-read notification-id]
:action :notification/mark-as-read
:before-test (fn []
(rf/dispatch [:test/assoc-in [:activity-center]
{:notifications {types/one-to-one-chat
{:all {:cursor "" :data [{:id notification-id
:read false
:type types/one-to-one-chat}]}
:unread {:cursor "" :data []}}}
:filter {:type types/one-to-one-chat
:status :all}}]))})))
;;;; Contact verification
(def contact-verification-rpc-response
{:activityCenterNotifications
@ -59,22 +151,6 @@
:timestamp 1666647286000
:type types/contact-verification})
(defn test-log-on-failure
[{:keys [notification-id event action]}]
(rf-test/run-test-sync
(setup)
(h/using-log-test-appender
(fn [logs]
(h/stub-fx-with-callbacks ::json-rpc/call :on-error (constantly :fake-error))
(rf/dispatch event)
(is (= {:args [(str "Failed to " action)
{:notification-id notification-id
:error :fake-error}]
:level :warn}
(last @logs)))))))
(defn test-contact-verification-event
[{:keys [event expected-rpc-call]}]
(rf-test/run-test-sync

View File

@ -51,9 +51,13 @@
{:button-1 {:label (i18n/label :t/decline)
:accessibility-label :decline-contact-request
:type :danger
:on-press #(rf/dispatch [:contact-requests.ui/decline-request id])}
:on-press (fn []
(rf/dispatch [:contact-requests.ui/decline-request id])
(rf/dispatch [:activity-center.notifications/mark-as-read id]))}
:button-2 {:label (i18n/label :t/accept)
:accessibility-label :accept-contact-request
:type :positive
:on-press #(rf/dispatch [:contact-requests.ui/accept-request id])}}
:on-press (fn []
(rf/dispatch [:contact-requests.ui/accept-request id])
(rf/dispatch [:activity-center.notifications/mark-as-read id]))}}
nil))])))

View File

@ -85,21 +85,29 @@
{:button-1 {:label (i18n/label :t/untrustworthy)
:accessibility-label :mark-contact-verification-as-untrustworthy
:type :danger
:on-press #(rf/dispatch [:activity-center.contact-verification/mark-as-untrustworthy id])}
:on-press (fn []
(rf/dispatch [:activity-center.contact-verification/mark-as-untrustworthy id])
(rf/dispatch [:activity-center.notifications/mark-as-read id]))}
:button-2 {:label (i18n/label :t/accept)
:accessibility-label :mark-contact-verification-as-trusted
:type :positive
:on-press #(rf/dispatch [:activity-center.contact-verification/mark-as-trusted id])}})
:on-press (fn []
(rf/dispatch [:activity-center.contact-verification/mark-as-trusted id])
(rf/dispatch [:activity-center.notifications/mark-as-read id]))}})
(when (= contact-verification-status constants/contact-verification-status-pending)
{:button-1 {:label (i18n/label :t/decline)
:accessibility-label :decline-contact-verification
:type :danger
:on-press #(hide-bottom-sheet-and-dispatch [:activity-center.contact-verification/decline id])}
:on-press (fn []
(hide-bottom-sheet-and-dispatch [:activity-center.contact-verification/decline id])
(rf/dispatch [:activity-center.notifications/mark-as-read id]))}
:button-2 (if replying?
{:label (i18n/label :t/send-reply)
:accessibility-label :reply-to-contact-verification
:type :primary
:on-press #(hide-bottom-sheet-and-dispatch [:activity-center.contact-verification/reply id @reply])}
:on-press (fn []
(hide-bottom-sheet-and-dispatch [:activity-center.contact-verification/reply id @reply])
(rf/dispatch [:activity-center.notifications/mark-as-read id]))}
{:label (i18n/label :t/message-reply)
:accessibility-label :send-reply-to-contact-verification
:type :primary

View File

@ -256,11 +256,11 @@
:width 32
:style {:margin-left 12}
:accessibility-label :notifications-button
:on-press #(do
(re-frame/dispatch [:mark-all-activity-center-notifications-as-read])
(if config/new-activity-center-enabled?
:on-press #(do (if config/new-activity-center-enabled?
(re-frame/dispatch [:activity-center/open])
(re-frame/dispatch [:navigate-to :notifications-center])))}
(do
(re-frame/dispatch [:mark-all-activity-center-notifications-as-read])
(re-frame/dispatch [:navigate-to :notifications-center]))))}
[icons/icon :main-icons/notification2 {:color (quo2.colors/theme-colors quo2.colors/neutral-100 quo2.colors/white)}]]
(when (pos? notif-count)
[react/view {:style (merge (styles/counter-public-container) {:top 5 :right 5})

View File

@ -9,10 +9,10 @@
[utils.re-frame :as rf]))
(defn navigate-to-activity-center []
(rf/dispatch [:mark-all-activity-center-notifications-as-read])
(if config/new-activity-center-enabled?
(rf/dispatch [:activity-center/open])
(rf/dispatch [:navigate-to :notifications-center])))
(do (rf/dispatch [:mark-all-activity-center-notifications-as-read])
(rf/dispatch [:navigate-to :notifications-center]))))
(defn title-column [{:keys [label handler accessibility-label]}]
[rn/view style/title-column

View File

@ -1,5 +1,6 @@
(ns status-im2.contexts.chat.home.contact-request.view
(:require [react-native.core :as rn]
[status-im2.setup.config :as config]
[quo2.core :as quo]
[i18n.i18n :as i18n]
[utils.re-frame :as rf]
@ -58,7 +59,8 @@
:on-press #(do
(rf/dispatch [:bottom-sheet/show-sheet
{:content (fn [] [contact-requests-sheet requests])}])
(rf/dispatch [:mark-all-activity-center-notifications-as-read]))
(when-not config/new-activity-center-enabled?
(rf/dispatch [:mark-all-activity-center-notifications-as-read])))
:style style/contact-requests}
[rn/view {:style (style/contact-requests-icon)}
[quo/icon :i/pending-user {:color (colors/theme-colors colors/neutral-50 colors/neutral-40)}]]