/* * Copyright (c) 2021-2022 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ #ifndef BASE_NOTIFICATION_DISTRIBUTED_NOTIFICATION_SERVICE_FRAMEWORKS_ANS_CORE_INCLUDE_REMINDER_DATA_MANAGER_H #define BASE_NOTIFICATION_DISTRIBUTED_NOTIFICATION_SERVICE_FRAMEWORKS_ANS_CORE_INCLUDE_REMINDER_DATA_MANAGER_H #include #include #include "advanced_notification_service.h" #include "ans_inner_errors.h" #ifdef PLAYER_FRAMEWORK_ENABLE #include "player.h" #endif #include "ffrt.h" #include "app_mgr_client.h" #include "reminder_request.h" #include "reminder_store.h" #include "reminder_timer_info.h" #include "reminder_config_change_observer.h" #include "datashare_predicates.h" #include "datashare_values_bucket.h" #include "app_mgr_interface.h" #include "time_service_client.h" namespace OHOS { namespace Notification { class ReminderDataManager final { public: ReminderDataManager() { Init(false); }; ~ReminderDataManager(); ReminderDataManager(ReminderDataManager &other) = delete; ReminderDataManager& operator = (const ReminderDataManager &other) = delete; /** * @brief Cancels all the reminders relative to the bundle option. * * @param packageName Indicates the package name. * @param userId Indicates the user id which the bundle belong to. * @param uid Indicates the uid which the bundle belong to. * @return ERR_OK if success, else not. */ ErrCode CancelAllReminders(const std::string& packageName, const int32_t userId, const int32_t uid); /** * @brief Cancels the target reminder relative to the reminder id and bundle option. * * @param reminderId Indicates the reminder id. * @param bundleOption Indicates the bundle option. * @return ERR_OK if success, else not. */ ErrCode CancelReminder(const int32_t &reminderId, const sptr &bundleOption); sptr CheckExcludeDateParam(const int32_t reminderId, const sptr &bundleOption); /** * @brief Add exclude date for reminder * * @param reminderId Identifies the reminders id. * @param date exclude date * @return Returns ERR_OK on success, others on failure. */ ErrCode AddExcludeDate(const int32_t reminderId, const uint64_t date, const sptr &bundleOption); /** * @brief Clear exclude date for reminder * * @param reminderId Identifies the reminders id. * @return Returns ERR_OK on success, others on failure. */ ErrCode DelExcludeDates(const int32_t reminderId, const sptr &bundleOption); /** * @brief Get exclude date for reminder * * @param reminderId Identifies the reminders id. * @param dates exclude dates * @return Returns ERR_OK on success, others on failure. */ ErrCode GetExcludeDates(const int32_t reminderId, const sptr &bundleOption, std::vector& dates); /** * @brief Close the target reminder which is showing on panel. * This is manul operation by user: 1.Click close button of the reminder, 2.remove reminder notification. * * @param want Want information that transferred when the event trigger by user. * @param cancelNotification Indicates whether need to cancel notification or not. */ void CloseReminder(const OHOS::EventFwk::Want &want, bool cancelNotification, bool isButtonClick = true); /** * Dump all the reminders information. * * @return reminders informations. */ std::string Dump() const; /** * Obtains the single instance. * * @return Single instance of ReminderDataManager. */ static std::shared_ptr GetInstance(); static std::shared_ptr InitInstance( const sptr &advancedNotificationService); /** * Obtains all the valid reminders (which are not expired) relative to the bundle option. * * @param bundleOption Indicates the bundle option. * @param[out] reminders return the valid reminders. */ void GetValidReminders( const sptr &bundleOption, std::vector> &reminders); /** * @brief Inits and recovery data from database. * * @param isFromBootComplete Indicates the init is called when boot completed. */ void Init(bool isFromBootComplete); void InitUserId(); /** * @brief Check all reminders, Whether an immediate reminder is needed; * whether a pull up service extension is required. * Use when powering on and changing the system time. */ void CheckReminderTime(std::vector>& immediatelyReminders, std::vector>& extensionReminders); /** * @brief Register configuration observer, the listening system language is changed. */ bool RegisterConfigurationObserver(); void OnUserRemove(const int32_t& userId); /** * @brief Bundle manager service start. */ void OnBundleMgrServiceStart(); /** * @brief Ability manager service start. */ void OnAbilityMgrServiceStart(); void OnUserSwitch(const int32_t& userId); /** * @brief Triggered when third party application died. * * @param bundleOption Indicates the bundleOption of third party application. */ void OnProcessDiedLocked(const sptr &bundleOption); /** * Publishs a scheduled reminder. * * @param reminder Indicates the reminder. * @param bundleOption Indicates bundle option the reminder belongs to. * @return ERR_OK if success, else not. */ ErrCode PublishReminder(const sptr &reminder, const sptr &bundleOption); /** * @brief Refresh all reminders when date/time or timeZone of device changed by user. * * @param type Indicates it is triggered by dateTime change or timeZone change. */ void RefreshRemindersDueToSysTimeChange(uint8_t type); /** * @brief Indicates the single instance of ans that used to execute operations in service. * * @param Indicates the single instance of ans notification service. */ void SetService(sptr &advancedNotificationService); bool ShouldAlert(const sptr &reminder) const; /** * @brief Show the reminder. * * @param isSysTimeChanged Indicates it is triggered as dateTime changed by user or not. * @param want Which contains the given reminder. */ void ShowActiveReminder(const EventFwk::Want &want); /** * @brief Snooze the reminder by manual. * 1) Snooze the trigger time to the next. * 2) Update the notification(Update notification lable/content...; Stop audio player and vibrator) * 3) Show the notification dialog in the SystemUI * 4) Start a new reminder, which is recent one now. * * @param want Which contains the given reminder. */ void SnoozeReminder(const OHOS::EventFwk::Want &want); /** * Starts the recent reminder timing. */ void StartRecentReminder(); /** * Handle custom button click event. */ void HandleCustomButtonClick(const OHOS::EventFwk::Want &want); /** * Handle click notification, no button. */ void ClickReminder(const OHOS::EventFwk::Want &want); /** * Handle auto delete time */ void HandleAutoDeleteReminder(const int32_t notificationId, const int32_t uid, const int64_t autoDeletedTime); /** * @brief Terminate the alerting reminder. * * 1. Stop sound and vibrate. * 2. Stop the alerting timer. * 3. Update the reminder state. * 4. Update the display content of the notification. * * @param want Which contains the given reminder. */ void TerminateAlerting(const OHOS::EventFwk::Want &want); /** * @brief Update reminders based on the system language. * * Update action button title. */ void UpdateReminderLanguageLocked(const int32_t uid, const std::vector>& reminders); /** * @brief System language change */ void OnLanguageChanged(); /** * @brief When OnRemoveSystemAbility occurs. */ void OnRemoveAppMgr(); /** * @brief Whether the device is ready or not. */ bool IsSystemReady(); static constexpr uint8_t TIME_ZONE_CHANGE = 0; static constexpr uint8_t DATE_TIME_CHANGE = 1; private: enum class TimerType : uint8_t { TRIGGER_TIMER, ALERTING_TIMER }; static std::shared_ptr serviceQueue_; /** * Add default slot to the reminder if no slot set by user. * * @param reminder Indicates the reminder. */ void AddDefaultSlotIfNeeded(sptr &reminder); /** * Add reminder to showed reminder vector. * * @param reminder Indicates the showed reminder. */ void AddToShowedReminders(const sptr &reminder); void CancelAllReminders(const int32_t userId); /** * @brief Check the update conditions. * * @param reminder Indicates the showed reminder. * @param actionButtonType Button type of the button. * @param actionButtonMap Button map. * @return True if check successful. */ bool CheckUpdateConditions(const sptr &reminder, const ReminderRequest::ActionButtonType &actionButtonType, const std::map &actionButtonMap); /** * @brief update app database. * * @param reminder Indicates the showed reminder. * @param actionButtonType Button type of the button. */ void UpdateAppDatabase(const sptr &reminder, const ReminderRequest::ActionButtonType &actionButtonType); /** * @brief generate Predicates for dataShare. * * @param predicates find fields from database. * @param equalToVector Split from dataShareUpdate->equaleTo. */ void GenPredicates(DataShare::DataSharePredicates &predicates, const std::vector &equalToVector); /** * @brief generate ValuesBucket for dataShare. * * @param valuesBucket update fields at database. * @param valuesBucketVector Split from dataShareUpdate->valuesBucket. */ void GenValuesBucket(DataShare::DataShareValuesBucket &valuesBucket, const std::vector &valuesBucketVector); /** * @brief get bundleName from uri. * * @param dstBundleName The package name required to update the database. * @param uri Database address. */ void GenDstBundleName(std::string &dstBundleName, const std::string &uri) const; /** * @brief get custom ring uri. * * @param reminder Indicates the reminder. * @return Returns the uri of ring tone. */ std::string GetCustomRingUri(const sptr &reminder); /** * @brief Cancels all the reminders of the target bundle or user. * * @param packageName Indicates the packageName need to cancel. * @param userId Indicates the userId to cancel. */ void CancelRemindersImplLocked(const std::string &packageName, const int32_t userId, const int32_t uid); /** * @brief Close reminders with the same group id. * * @param oldReminderId Indicates the reminderId that are currently bing showed. * @param packageName Indicates the packageName need to cancel. * @param groupId Indicates the group id to cancel. */ void CloseRemindersByGroupId(const int32_t &oldReminderId, const std::string &packageName, const std::string &groupId); /** * Cancels the notification relative to the reminder. * * @param reminder Indicates the reminder. */ void CancelNotification(const sptr &reminder) const; /** * Check whether the number limit of reminders if exceeded. * * @param bundleName Indicates the target bundle. * @return true if number limit is exceeded. */ bool CheckReminderLimitExceededLocked(const sptr &bundleOption, const sptr &reminder) const; void CloseReminder(const sptr &reminder, bool cancelNotification); /** * Create a information for timer, such as timer type, repeat policy, interval and want agent. * * @param type Indicates the timer type. * @param reminderRequest Indicates the reminder request. * @return pointer of ReminderTimerInfo. */ std::shared_ptr CreateTimerInfo(TimerType type, const sptr &reminderRequest) const; void InitTimerInfo(std::shared_ptr &timerInfo, const sptr &reminderRequest, TimerType reminderType) const; void GetImmediatelyShowRemindersLocked(std::vector> &reminders) const; std::string GetSoundUri(const sptr &reminder); /** * Find the reminder from reminderVector_ by reminder id. * * @param reminderId Indicates the reminder id. * @return pointer of reminder request or nullptr. */ sptr FindReminderRequestLocked(const int32_t &reminderId); /** * Find the reminder from {@link reminderVector_} and * {@link notificationBundleOptionMap_} by reminder id and pkgName. * * @param reminderId Indicates the reminder id. * @param pkgName Indicates the package name. * @return pointer of reminder request or nullptr. */ sptr FindReminderRequestLocked(const int32_t &reminderId, const std::string &pkgName); /** * Obtains the recent reminder which is not expired from reminder vector. * * The expired reminders will be removed from reminderVector_ and notificationBundleOptionMap_. * * @return pointer of reminder object. */ sptr GetRecentReminderLocked(); void HandleImmediatelyShow(std::vector> &showImmediately, bool isSysTimeChanged); void HandleExtensionReminder(std::vector> &extensionReminders, const int8_t type); /** * @brief Refresh the reminder due to date/time or timeZone change by user. * * @param type Indicates it is date/time change or timeZone change. * @param reminder Indicates the target reminder. * @return sptr Returns the target reminder if it is need to show immediately, otherwise nullptr. */ sptr HandleRefreshReminder(const uint8_t &type, sptr &reminder); /** * @brief Handles all the reminders that have the same notification id and belong to same application * with the current reminder. Unset the state of "showing". * * @param reminder Indicates the current reminder. */ void HandleSameNotificationIdShowing(const sptr reminder); bool HandleSysTimeChange(const sptr reminder) const; /** * @brief Judge the two reminders is belong to the same application or not. * * @param bundleOption Indicates the bundleOption of first reminder. * @param other Indicates the bundleOption of second reminder. * @return true if the two reminders belong to the same application. */ bool IsBelongToSameApp(const sptr &bundleOption, const sptr &other) const; bool CheckIsSameApp(const sptr &reminder, const sptr &other) const; /** * @brief Judges whether the reminder is matched with the bundleOption or userId. * * @param reminder Indicates the target reminder. * @param packageName Indicates the package name. * @param userId Indicates the user id. * @param uid Indicates the uid. * @return true If the reminder is matched with the bundleOption or userId. */ bool IsMatched(const sptr &reminder, const std::string &packageName, const int32_t userId, const int32_t uid) const; /** * @brief Judges whether the reminder is matched with the packageName or groupId. * * @param reminder Indicates the target reminder. * @param packageName Indicates the package name. * @param groupId Indicates the group id. * @return true If the reminder is matched with the packageName and groupId. */ bool IsMatchedForGroupIdAndPkgName(const sptr &reminder, const std::string &packageName, const std::string &groupId) const; bool IsAllowedNotify(const sptr &reminder) const; bool IsReminderAgentReady() const; void LoadReminderFromDb(); void PlaySoundAndVibrationLocked(const sptr &reminder); void PlaySoundAndVibration(const sptr &reminder); void StopSoundAndVibrationLocked(const sptr &reminder); void StopSoundAndVibration(const sptr &reminder); /** * Remove from showed reminder vector. * * @param reminder Indicates the reminder need to remove. */ void RemoveFromShowedReminders(const sptr &reminder); /** * @brief Refresh the all reminders due to date/time or timeZone change by user. * * @param type Indicates it is date/time change or timeZone change. * @return reminders that need to show immediately. */ void RefreshRemindersLocked(uint8_t type, std::vector>& immediatelyReminders, std::vector>& extensionReminders); /** * Removes the reminder. * 1. removes the reminder from reminderVector_ and notificationBundleOptionMap_. * 2. cancels the notification. * * @param reminderId Indicates the reminder id. */ void RemoveReminderLocked(const int32_t &reminderId); /** * Resets timer status. * 1. Sets timerId_ or timerIdAlerting_ with 0. * 2. Sets activeReminderId_ or alertingReminderId with -1. * * @param type Indicates the timer type. */ void ResetStates(TimerType type); void SetActiveReminder(const sptr &reminder); void SetAlertingReminder(const sptr &reminder); void ShowActiveReminderExtendLocked(sptr &reminder, std::vector>& extensionReminders); static bool StartExtensionAbility(const sptr &reminder, const int8_t type); static void AsyncStartExtensionAbility(const sptr &reminder, int32_t times, const int8_t type); void InitServiceHandler(); /** * @brief Show the reminder on SystemUI. * * @param reminder Indicates the reminder to show. * @param isNeedToPlaySound Indicates whether need to play sound. * @param isNeedToStartNext Indicates whether need to start next reminder. * @param isSysTimeChanged Indicates whether it is triggerred as system time changed by user. * @param needScheduleTimeout Indicates whether need to control the ring duration. */ void ShowReminder(const sptr &reminder, const bool &isNeedToPlaySound, const bool &isNeedToStartNext, const bool &isSysTimeChanged, const bool &needScheduleTimeout); void SnoozeReminderImpl(sptr &reminder); /** * Starts timing actually. * * @param reminderRequest Indicates the reminder. * @param type Indicates the timer type. */ void StartTimerLocked(const sptr &reminderRequest, TimerType type); void StartTimer(const sptr &reminderRequest, TimerType type); uint64_t HandleTriggerTimeInner(const sptr &reminderRequest, TimerType type, const sptr &timer); uint64_t HandleAlertingTimeInner(const sptr &reminderRequest, TimerType type, const sptr &timer, time_t now); /** * @brief Stop the alerting timer and update reminder information. * * 1. Stop sound and vibrate. * 2. Stop the alerting timer. * * @param reminder Indicates the target reminder. */ void StopAlertingReminder(const sptr &reminder); /** * Stops timing. * * @param type Indicates the timer type. */ void StopTimer(TimerType type); void StopTimerLocked(TimerType type); /** * @brief Terminate the alerting reminder. * * 1. Stop sound and vibrate. * 2. Stop the alerting timer. * 3. Update the reminder state. * 4. Update the display content of the notification. * * @param reminder Indicates the reminder. * @param reason Indicates the description information. */ void TerminateAlerting(const sptr &reminder, const std::string &reason); void TerminateAlerting(const uint16_t waitInSecond, const sptr &reminder); /** * @brief Assign unique reminder id and save reminder in memory. * * @param reminder Indicates a reminder. * @param bundleOption Indicates bundle option relative to the reminder. */ void UpdateAndSaveReminderLocked( const sptr &reminder, const sptr &bundleOption); void UpdateNotification(const sptr &reminder, bool isSnooze); static bool cmp(sptr &reminderRequest, sptr &other); /** * @brief Connect App Manager to get the current foreground application. */ bool ConnectAppMgr(); /** * @brief Check need to notify the application, if the current foreground application * is the creator of the reminder, notify the application of the reminder status * change; otherwise, do not noitfy. * * @param reminder Indicates a reminder. * @param buttonType The type of button clicked by the user. */ void CheckNeedNotifyStatus(const sptr &reminder, const ReminderRequest::ActionButtonType buttonType); std::string GetFullPath(const std::string& path); /** * @brief Check action button data share permission */ bool IsActionButtonDataShareValid(const sptr& reminder, const uint32_t callerTokenId); /** * @brief Get resource manager by bundlename and uid. */ std::shared_ptr GetResourceMgr(const std::string& bundleName, const int32_t uid); /** * @brief Get custom ring file desc. * lock by resourceMutex_ in function */ bool GetCustomRingFileDesc(const sptr& reminder, Global::Resource::ResourceManager::RawFileDescriptor& desc); /** * @brief Close custom ring file desc. * lock by resourceMutex_ in function */ void CloseCustomRingFileDesc(const int32_t reminderId, const std::string& customRingUri); /** * @brief report event to dfx */ void ReportSysEvent(const sptr& reminder); ErrCode PublishNotificationRequest(sptr& request, const sptr& bundleOption); bool CheckShowLimit(std::unordered_map& limits, int32_t& totalCount, sptr& reminder); /** * Single instance. */ static std::shared_ptr REMINDER_DATA_MANAGER; /** * Used for multi-thread synchronise. */ static std::mutex MUTEX; static std::mutex SHOW_MUTEX; static std::mutex ALERT_MUTEX; static std::mutex TIMER_MUTEX; static std::mutex ACTIVE_MUTEX; /** * Max number of reminders limit for the whole system. */ static constexpr int16_t MAX_NUM_REMINDER_LIMIT_SYSTEM = 12000; /** * Max number of reminders limit for one system application. */ static constexpr int16_t MAX_NUM_REMINDER_LIMIT_SYS_APP = 10000; /** * Max number of reminders limit for one application. */ static constexpr int16_t MAX_NUM_REMINDER_LIMIT_APP = 30; bool isReminderAgentReady_ = false; /** * Vector used to record all the reminders in system. */ std::vector> reminderVector_; /** * Vector used to record all the reminders which has been shown on panel. */ std::vector> showedReminderVector_; /** * This timer is used to control the triggerTime of next reminder. */ uint64_t timerId_ {0}; /** * This timer is used to control the ringDuration of the alerting reminder. */ std::atomic timerIdAlerting_ {0}; /** * Indicates the active reminder that timing is taking effect. */ std::atomic activeReminderId_ = -1; sptr activeReminder_ = nullptr; /** * Indicates the reminder which is playing sound or vibration. */ std::atomic alertingReminderId_ = -1; sptr alertingReminder_ = nullptr; #ifdef PLAYER_FRAMEWORK_ENABLE std::shared_ptr soundPlayer_ = nullptr; std::mutex resourceMutex_; // for soundResource_ std::shared_ptr soundResource_ = nullptr; #endif /** * Indicates the total count of reminders in system. */ int16_t totalCount_ {0}; int currentUserId_ {0}; sptr advancedNotificationService_ = nullptr; std::shared_ptr store_ = nullptr; /** * Indicates config change observer for language */ sptr configChangeObserver_ = nullptr; /** * Indicates app mananger for get foreground application */ std::mutex appMgrMutex_; sptr appMgrProxy_ = nullptr; /** * async queue */ std::shared_ptr queue_ = nullptr; /** * Sa ready flag */ std::atomic saReadyFlag_{ 0 }; }; } // namespace OHOS } // namespace Notification #endif // BASE_NOTIFICATION_DISTRIBUTED_NOTIFICATION_SERVICE_FRAMEWORKS_ANS_CORE_INCLUDE_REMINDER_DATA_MANAGER_H