1 /*
2 * Copyright (C) 2025 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "distributed_subscribe_service.h"
17
18 #include "analytics_util.h"
19 #include "os_account_manager.h"
20 #include "distributed_data_define.h"
21 #include "notification_helper.h"
22 #include "distributed_device_service.h"
23 #include "notification_subscribe_info.h"
24
25 namespace OHOS {
26 namespace Notification {
27
28 const int32_t FILTER_IM_TYPE = 1;
29 const int32_t FILTER_IM_REPLY_TYPE = 2;
30
GetCurrentActiveUserId()31 int32_t DistributedSubscribeService::GetCurrentActiveUserId()
32 {
33 int32_t userId = DEFAULT_USER_ID;
34 int32_t ret = OHOS::AccountSA::OsAccountManager::GetForegroundOsAccountLocalId(userId);
35 if (ret != ERR_OK) {
36 ANS_LOGW("Dans get Current userId failed %{public}d.", ret);
37 return DEFAULT_USER_ID;
38 }
39 return userId;
40 }
41
GetInstance()42 DistributedSubscribeService& DistributedSubscribeService::GetInstance()
43 {
44 static DistributedSubscribeService distributedSubscribeService;
45 return distributedSubscribeService;
46 }
47
SubscribeNotification(const DistributedDeviceInfo device)48 void DistributedSubscribeService::SubscribeNotification(const DistributedDeviceInfo device)
49 {
50 DistributedDeviceInfo peerDevice;
51 if (!DistributedDeviceService::GetInstance().GetDeviceInfo(device.deviceId_, peerDevice)) {
52 ANS_LOGI("Local device no %{public}s .", StringAnonymous(device.deviceId_).c_str());
53 return;
54 }
55
56 int32_t userId = GetCurrentActiveUserId();
57 std::shared_ptr<DistribuedSubscriber> subscriber = std::make_shared<DistribuedSubscriber>();
58 subscriber->SetLocalDevice(DistributedDeviceService::GetInstance().GetLocalDevice());
59 subscriber->SetPeerDevice(peerDevice);
60 sptr<NotificationSubscribeInfo> subscribeInfo = new NotificationSubscribeInfo();
61 if (peerDevice.deviceType_ == DistributedHardware::DmDeviceType::DEVICE_TYPE_WATCH) {
62 std::vector<NotificationConstant::SlotType> slotTypes;
63 slotTypes.push_back(NotificationConstant::SlotType::LIVE_VIEW);
64 slotTypes.push_back(NotificationConstant::SlotType::SOCIAL_COMMUNICATION);
65 subscribeInfo->SetSlotTypes(slotTypes);
66 subscribeInfo->SetFilterType(FILTER_IM_TYPE);
67 }
68 subscribeInfo->AddDeviceType(DistributedDeviceService::DeviceTypeToTypeString(peerDevice.deviceType_));
69 subscribeInfo->AddAppUserId(userId);
70 subscribeInfo->SetNeedNotifyApplication(true);
71 subscribeInfo->SetNeedNotifyResponse(true);
72 int result = NotificationHelper::SubscribeNotification(subscriber, subscribeInfo);
73 if (result == 0) {
74 std::lock_guard<ffrt::mutex> lock(mapLock_);
75 auto iter = subscriberMap_.find(peerDevice.deviceId_);
76 if (iter != subscriberMap_.end()) {
77 NotificationHelper::UnSubscribeNotification(iter->second);
78 }
79 subscriberMap_[peerDevice.deviceId_] = subscriber;
80 DistributedDeviceService::GetInstance().SetDeviceState(peerDevice.deviceId_, DeviceState::STATE_ONLINE);
81 std::string reason = "deviceType: " + std::to_string(peerDevice.deviceType_) +
82 " ; deviceId: " + StringAnonymous(peerDevice.deviceId_);
83 AnalyticsUtil::GetInstance().SendHaReport(PUBLISH_ERROR_EVENT_CODE, 0, BRANCH3_ID, reason);
84 }
85 ANS_LOGI("Subscribe notification %{public}s %{public}d %{public}d %{public}d.",
86 StringAnonymous(peerDevice.deviceId_).c_str(), peerDevice.deviceType_, userId, result);
87 }
88
UnSubscribeNotification(const std::string & deviceId,uint16_t deviceType,bool releaseDevice)89 void DistributedSubscribeService::UnSubscribeNotification(const std::string &deviceId, uint16_t deviceType,
90 bool releaseDevice)
91 {
92 if (releaseDevice) {
93 DistributedDeviceService::GetInstance().DeleteDeviceInfo(deviceId);
94 }
95 std::lock_guard<ffrt::mutex> lock(mapLock_);
96 auto iter = subscriberMap_.find(deviceId);
97 if (iter == subscriberMap_.end()) {
98 ANS_LOGI("UnSubscribe invalid %{public}s.", StringAnonymous(deviceId).c_str());
99 return;
100 }
101
102 int32_t result = NotificationHelper::UnSubscribeNotification(iter->second);
103 if (result == ERR_OK) {
104 subscriberMap_.erase(deviceId);
105 }
106 std::string message = "UnSubscribe: " + StringAnonymous(deviceId) + " type: " + std::to_string(deviceType);
107 AnalyticsUtil::GetInstance().SendHaReport(OPERATION_DELETE_BRANCH, result, BRANCH2_ID, message,
108 PUBLISH_ERROR_EVENT_CODE);
109 ANS_LOGI("UnSubscribe notification %{public}s %{public}d.", StringAnonymous(deviceId).c_str(), deviceType);
110 }
111
UnSubscribeAllNotification()112 void DistributedSubscribeService::UnSubscribeAllNotification()
113 {
114 std::lock_guard<ffrt::mutex> lock(mapLock_);
115 for (auto& subscriberInfo : subscriberMap_) {
116 int32_t result = NotificationHelper::UnSubscribeNotification(subscriberInfo.second);
117 ANS_LOGI("UnSubscribe %{public}s %{public}d.", subscriberInfo.first.c_str(), result);
118 }
119 }
120
121 }
122 }
123
124