1bc2ed2b3Sopenharmony_ci/*
2bc2ed2b3Sopenharmony_ci * Copyright (C) 2024 Huawei Device Co., Ltd.
3bc2ed2b3Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License");
4bc2ed2b3Sopenharmony_ci * you may not use this file except in compliance with the License.
5bc2ed2b3Sopenharmony_ci * You may obtain a copy of the License at
6bc2ed2b3Sopenharmony_ci *
7bc2ed2b3Sopenharmony_ci *     http://www.apache.org/licenses/LICENSE-2.0
8bc2ed2b3Sopenharmony_ci *
9bc2ed2b3Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software
10bc2ed2b3Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS,
11bc2ed2b3Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12bc2ed2b3Sopenharmony_ci * See the License for the specific language governing permissions and
13bc2ed2b3Sopenharmony_ci * limitations under the License.
14bc2ed2b3Sopenharmony_ci */
15bc2ed2b3Sopenharmony_ci
16bc2ed2b3Sopenharmony_ci#include "nfc_notification.h"
17bc2ed2b3Sopenharmony_ci
18bc2ed2b3Sopenharmony_ci#include <map>
19bc2ed2b3Sopenharmony_ci
20bc2ed2b3Sopenharmony_ci#include "cJSON.h"
21bc2ed2b3Sopenharmony_ci#include "file_ex.h"
22bc2ed2b3Sopenharmony_ci#include "locale_config.h"
23bc2ed2b3Sopenharmony_ci#include "locale_info.h"
24bc2ed2b3Sopenharmony_ci#include "loghelper.h"
25bc2ed2b3Sopenharmony_ci#include "nfc_sdk_common.h"
26bc2ed2b3Sopenharmony_ci#include "securec.h"
27bc2ed2b3Sopenharmony_ci#include "want_agent_helper.h"
28bc2ed2b3Sopenharmony_ci#include "want_agent_info.h"
29bc2ed2b3Sopenharmony_ci
30bc2ed2b3Sopenharmony_ci#ifdef DEBUG
31bc2ed2b3Sopenharmony_ci#undef DEBUG
32bc2ed2b3Sopenharmony_ci#endif
33bc2ed2b3Sopenharmony_ci#include "notification_helper.h"
34bc2ed2b3Sopenharmony_ci
35bc2ed2b3Sopenharmony_cinamespace OHOS {
36bc2ed2b3Sopenharmony_cinamespace NFC {
37bc2ed2b3Sopenharmony_cinamespace TAG {
38bc2ed2b3Sopenharmony_cistatic std::string g_sysLanguage = "";
39bc2ed2b3Sopenharmony_cistatic std::map<std::string, std::string> g_resourceMap;
40bc2ed2b3Sopenharmony_cistatic std::mutex g_callbackMutex {};
41bc2ed2b3Sopenharmony_cistatic NfcNtfCallback g_ntfCallback = nullptr;
42bc2ed2b3Sopenharmony_ci
43bc2ed2b3Sopenharmony_ciclass NfcNotificationSubscriber : public Notification::NotificationSubscriber {
44bc2ed2b3Sopenharmony_ci    void OnConnected() {}
45bc2ed2b3Sopenharmony_ci    void OnDisconnected() {}
46bc2ed2b3Sopenharmony_ci    void OnUpdate(const std::shared_ptr<Notification::NotificationSortingMap> &sortingMap) {}
47bc2ed2b3Sopenharmony_ci    void OnDoNotDisturbDateChange(const std::shared_ptr<Notification::NotificationDoNotDisturbDate> &date) {}
48bc2ed2b3Sopenharmony_ci    void OnEnabledNotificationChanged(
49bc2ed2b3Sopenharmony_ci        const std::shared_ptr<Notification::EnabledNotificationCallbackData> &callbackData) {}
50bc2ed2b3Sopenharmony_ci    void OnDied() {}
51bc2ed2b3Sopenharmony_ci    void OnCanceled(const std::shared_ptr<OHOS::Notification::Notification> &request,
52bc2ed2b3Sopenharmony_ci        const std::shared_ptr<Notification::NotificationSortingMap> &sortingMap, int deleteReason)
53bc2ed2b3Sopenharmony_ci    {
54bc2ed2b3Sopenharmony_ci        int creatorUid = request->GetUid();
55bc2ed2b3Sopenharmony_ci        int notificationId = request->GetId();
56bc2ed2b3Sopenharmony_ci        InfoLog("Oncanceled, creatorUid = %{public}d, notificationId = %{public}d, deleteReason = %{public}d",
57bc2ed2b3Sopenharmony_ci            creatorUid, notificationId, deleteReason);
58bc2ed2b3Sopenharmony_ci
59bc2ed2b3Sopenharmony_ci        std::lock_guard<std::mutex> lock(g_callbackMutex);
60bc2ed2b3Sopenharmony_ci        if (deleteReason == Notification::NotificationConstant::CLICK_REASON_DELETE && g_ntfCallback) {
61bc2ed2b3Sopenharmony_ci            g_ntfCallback(notificationId % OHOS::NFC::TAG::NTF_COUNT_CONSTANT);
62bc2ed2b3Sopenharmony_ci        }
63bc2ed2b3Sopenharmony_ci    }
64bc2ed2b3Sopenharmony_ci    void OnConsumed(const std::shared_ptr<OHOS::Notification::Notification> &notification,
65bc2ed2b3Sopenharmony_ci        const std::shared_ptr<Notification::NotificationSortingMap> &sortingMap) {}
66bc2ed2b3Sopenharmony_ci    void OnBadgeChanged(const std::shared_ptr<Notification::BadgeNumberCallbackData> &badgeData) {}
67bc2ed2b3Sopenharmony_ci    void OnBadgeEnabledChanged(const sptr<Notification::EnabledNotificationCallbackData> &callbackData) {}
68bc2ed2b3Sopenharmony_ci    void OnBatchCanceled(const std::vector<std::shared_ptr<OHOS::Notification::Notification>> &requestList,
69bc2ed2b3Sopenharmony_ci        const std::shared_ptr<Notification::NotificationSortingMap> &sortingMap, int32_t deleteReason) {}
70bc2ed2b3Sopenharmony_ci};
71bc2ed2b3Sopenharmony_ci
72bc2ed2b3Sopenharmony_cistatic std::shared_ptr<NfcNotificationSubscriber> g_notificationSubscriber
73bc2ed2b3Sopenharmony_ci    = std::make_shared<NfcNotificationSubscriber>();
74bc2ed2b3Sopenharmony_ci
75bc2ed2b3Sopenharmony_cistatic void UpdateResourceMap(const std::string &resourcePath)
76bc2ed2b3Sopenharmony_ci{
77bc2ed2b3Sopenharmony_ci    InfoLog("Reading resource string from json config.");
78bc2ed2b3Sopenharmony_ci
79bc2ed2b3Sopenharmony_ci    std::string content;
80bc2ed2b3Sopenharmony_ci    LoadStringFromFile(resourcePath, content);
81bc2ed2b3Sopenharmony_ci    cJSON *json = cJSON_Parse(content.c_str());
82bc2ed2b3Sopenharmony_ci    if (json == nullptr) {
83bc2ed2b3Sopenharmony_ci        ErrorLog("json nullptr.");
84bc2ed2b3Sopenharmony_ci        return;
85bc2ed2b3Sopenharmony_ci    }
86bc2ed2b3Sopenharmony_ci
87bc2ed2b3Sopenharmony_ci    cJSON *resJson = cJSON_GetObjectItemCaseSensitive(json, KEY_STRING);
88bc2ed2b3Sopenharmony_ci    if (resJson == nullptr || cJSON_GetArraySize(resJson) > MAX_RES_VEC_LEN) {
89bc2ed2b3Sopenharmony_ci        ErrorLog("fail to parse res json");
90bc2ed2b3Sopenharmony_ci        cJSON_Delete(json);
91bc2ed2b3Sopenharmony_ci        return;
92bc2ed2b3Sopenharmony_ci    }
93bc2ed2b3Sopenharmony_ci
94bc2ed2b3Sopenharmony_ci    g_resourceMap.clear();
95bc2ed2b3Sopenharmony_ci    cJSON *resJsonEach = nullptr;
96bc2ed2b3Sopenharmony_ci    cJSON_ArrayForEach(resJsonEach, resJson) {
97bc2ed2b3Sopenharmony_ci        cJSON *key = cJSON_GetObjectItemCaseSensitive(resJsonEach, KEY_NAME);
98bc2ed2b3Sopenharmony_ci        if (key == nullptr || !cJSON_IsString(key)) {
99bc2ed2b3Sopenharmony_ci            ErrorLog("json param not string");
100bc2ed2b3Sopenharmony_ci            cJSON_Delete(json);
101bc2ed2b3Sopenharmony_ci            return;
102bc2ed2b3Sopenharmony_ci        }
103bc2ed2b3Sopenharmony_ci
104bc2ed2b3Sopenharmony_ci        cJSON *value = cJSON_GetObjectItemCaseSensitive(resJsonEach, KEY_VALUE);
105bc2ed2b3Sopenharmony_ci        if (value == nullptr || !cJSON_IsString(value)) {
106bc2ed2b3Sopenharmony_ci            ErrorLog("json param not string");
107bc2ed2b3Sopenharmony_ci            cJSON_Delete(json);
108bc2ed2b3Sopenharmony_ci            return;
109bc2ed2b3Sopenharmony_ci        }
110bc2ed2b3Sopenharmony_ci
111bc2ed2b3Sopenharmony_ci        g_resourceMap.insert(std::pair<std::string, std::string>(key->valuestring, value->valuestring));
112bc2ed2b3Sopenharmony_ci    }
113bc2ed2b3Sopenharmony_ci    cJSON_Delete(json);
114bc2ed2b3Sopenharmony_ci}
115bc2ed2b3Sopenharmony_ci
116bc2ed2b3Sopenharmony_cistatic void UpdateResourceMapByLanguage()
117bc2ed2b3Sopenharmony_ci{
118bc2ed2b3Sopenharmony_ci    std::string curSysLanguage = "zh";
119bc2ed2b3Sopenharmony_ci    OHOS::Global::I18n::LocaleInfo locale(Global::I18n::LocaleConfig::GetSystemLocale());
120bc2ed2b3Sopenharmony_ci    curSysLanguage = locale.GetLanguage();
121bc2ed2b3Sopenharmony_ci    if (g_sysLanguage == curSysLanguage) {
122bc2ed2b3Sopenharmony_ci        DebugLog("same language environment, no need to update resource map.");
123bc2ed2b3Sopenharmony_ci        return;
124bc2ed2b3Sopenharmony_ci    }
125bc2ed2b3Sopenharmony_ci
126bc2ed2b3Sopenharmony_ci    InfoLog("current system language[%{public}s] changes, should update resource map", curSysLanguage.c_str());
127bc2ed2b3Sopenharmony_ci    g_sysLanguage = curSysLanguage;
128bc2ed2b3Sopenharmony_ci
129bc2ed2b3Sopenharmony_ci    if (g_sysLanguage == "en") {
130bc2ed2b3Sopenharmony_ci        UpdateResourceMap(NFC_RES_EN_JSON_FILEPATH);
131bc2ed2b3Sopenharmony_ci    } else {
132bc2ed2b3Sopenharmony_ci        UpdateResourceMap(NFC_RES_DEFAULT_JSON_FILEPATH);
133bc2ed2b3Sopenharmony_ci    }
134bc2ed2b3Sopenharmony_ci}
135bc2ed2b3Sopenharmony_ci
136bc2ed2b3Sopenharmony_cistatic std::string GetTrafficCardNotificationText(const std::string &cardName, int balance)
137bc2ed2b3Sopenharmony_ci{
138bc2ed2b3Sopenharmony_ci    char buf[MAX_BUFF_LEN] = {0};
139bc2ed2b3Sopenharmony_ci    int ret = sprintf_s(buf, MAX_BUFF_LEN, g_resourceMap[KEY_TRANSPORT_CARD_NTF_TEXT].c_str(),
140bc2ed2b3Sopenharmony_ci        g_resourceMap[cardName].c_str(), static_cast<float>(balance) / NFC_UNIT_CHANGE_CONSTANT);
141bc2ed2b3Sopenharmony_ci    if (ret <= 0) {
142bc2ed2b3Sopenharmony_ci        ErrorLog("sprintf_s failed, ret[%{public}d]", ret);
143bc2ed2b3Sopenharmony_ci        return "";
144bc2ed2b3Sopenharmony_ci    }
145bc2ed2b3Sopenharmony_ci
146bc2ed2b3Sopenharmony_ci    return std::string(buf);
147bc2ed2b3Sopenharmony_ci}
148bc2ed2b3Sopenharmony_ci
149bc2ed2b3Sopenharmony_ci#ifdef NDEF_WIFI_ENABLED
150bc2ed2b3Sopenharmony_cistatic std::string GetWifiNotificationText(const std::string &ssid)
151bc2ed2b3Sopenharmony_ci{
152bc2ed2b3Sopenharmony_ci    char buf[MAX_BUFF_LEN] = {0};
153bc2ed2b3Sopenharmony_ci    int ret = sprintf_s(buf, MAX_BUFF_LEN, g_resourceMap[KEY_NFC_WIFI_NTF_TEXT].c_str(), ssid.c_str());
154bc2ed2b3Sopenharmony_ci    if (ret <= 0) {
155bc2ed2b3Sopenharmony_ci        ErrorLog("sprintf_s failed, ret[%{public}d]", ret);
156bc2ed2b3Sopenharmony_ci        return "";
157bc2ed2b3Sopenharmony_ci    }
158bc2ed2b3Sopenharmony_ci
159bc2ed2b3Sopenharmony_ci    return std::string(buf);
160bc2ed2b3Sopenharmony_ci}
161bc2ed2b3Sopenharmony_ci#endif
162bc2ed2b3Sopenharmony_ci
163bc2ed2b3Sopenharmony_ci#ifdef NDEF_BT_ENABLED
164bc2ed2b3Sopenharmony_cistatic std::string GetBtNotificationText(const std::string &name)
165bc2ed2b3Sopenharmony_ci{
166bc2ed2b3Sopenharmony_ci    char buf[MAX_BUFF_LEN] = {0};
167bc2ed2b3Sopenharmony_ci    int ret = sprintf_s(buf, MAX_BUFF_LEN, g_resourceMap[KEY_NFC_BT_NTF_TEXT].c_str(), name.c_str());
168bc2ed2b3Sopenharmony_ci    if (ret <= 0) {
169bc2ed2b3Sopenharmony_ci        ErrorLog("sprintf_s failed, ret[%{public}d]", ret);
170bc2ed2b3Sopenharmony_ci        return "";
171bc2ed2b3Sopenharmony_ci    }
172bc2ed2b3Sopenharmony_ci
173bc2ed2b3Sopenharmony_ci    return std::string(buf);
174bc2ed2b3Sopenharmony_ci}
175bc2ed2b3Sopenharmony_ci#endif
176bc2ed2b3Sopenharmony_ci
177bc2ed2b3Sopenharmony_cistatic bool SetTitleAndTextForOtherNotificationId(int notificationId,
178bc2ed2b3Sopenharmony_ci    std::shared_ptr<Notification::NotificationNormalContent> nfcContent, const std::string &name, int balance)
179bc2ed2b3Sopenharmony_ci{
180bc2ed2b3Sopenharmony_ci    switch (notificationId) {
181bc2ed2b3Sopenharmony_ci        case NFC_TAG_DEFAULT_NTF_ID:
182bc2ed2b3Sopenharmony_ci            if (g_resourceMap.find(KEY_TAG_DEFAULT_NTF_TITLE) != g_resourceMap.end() &&
183bc2ed2b3Sopenharmony_ci                g_resourceMap.find(KEY_TAG_DEFAULT_NTF_TEXT) != g_resourceMap.end()) {
184bc2ed2b3Sopenharmony_ci                nfcContent->SetTitle(g_resourceMap[KEY_TAG_DEFAULT_NTF_TITLE]);
185bc2ed2b3Sopenharmony_ci                nfcContent->SetText(g_resourceMap[KEY_TAG_DEFAULT_NTF_TEXT]);
186bc2ed2b3Sopenharmony_ci            }
187bc2ed2b3Sopenharmony_ci            break;
188bc2ed2b3Sopenharmony_ci        case NFC_BROWSER_NOTIFICATION_ID:
189bc2ed2b3Sopenharmony_ci            if (g_resourceMap.find(KEY_TAG_DEFAULT_NTF_TITLE) != g_resourceMap.end() &&
190bc2ed2b3Sopenharmony_ci                g_resourceMap.find(NFC_OPEN_LINK_TEXT_HEAD) != g_resourceMap.end()) {
191bc2ed2b3Sopenharmony_ci                nfcContent->SetTitle(g_resourceMap[KEY_TAG_DEFAULT_NTF_TITLE]);
192bc2ed2b3Sopenharmony_ci                nfcContent->SetText(g_resourceMap[NFC_OPEN_LINK_TEXT_HEAD] + name);
193bc2ed2b3Sopenharmony_ci            }
194bc2ed2b3Sopenharmony_ci            break;
195bc2ed2b3Sopenharmony_ci        case NFC_HCE_AID_CONFLICTED_ID:
196bc2ed2b3Sopenharmony_ci            if (g_resourceMap.find(KEY_HCE_AID_CONFLICTED_TITLE) != g_resourceMap.end() &&
197bc2ed2b3Sopenharmony_ci                g_resourceMap.find(KEY_HCE_AID_CONFLICTED_TEXT) != g_resourceMap.end()) {
198bc2ed2b3Sopenharmony_ci                nfcContent->SetTitle(g_resourceMap[KEY_HCE_AID_CONFLICTED_TITLE]);
199bc2ed2b3Sopenharmony_ci                nfcContent->SetText(g_resourceMap[KEY_HCE_AID_CONFLICTED_TEXT]);
200bc2ed2b3Sopenharmony_ci            }
201bc2ed2b3Sopenharmony_ci            break;
202bc2ed2b3Sopenharmony_ci        case NFC_NO_HAP_SUPPORTED_NOTIFICATION_ID:
203bc2ed2b3Sopenharmony_ci            if (g_resourceMap.find(KEY_NO_HAP_TITLE) != g_resourceMap.end() &&
204bc2ed2b3Sopenharmony_ci                g_resourceMap.find(KEY_NO_HAP_TEXT) != g_resourceMap.end()) {
205bc2ed2b3Sopenharmony_ci                nfcContent->SetTitle(g_resourceMap[KEY_NO_HAP_TITLE]);
206bc2ed2b3Sopenharmony_ci                nfcContent->SetText(g_resourceMap[KEY_NO_HAP_TEXT]);
207bc2ed2b3Sopenharmony_ci            }
208bc2ed2b3Sopenharmony_ci            break;
209bc2ed2b3Sopenharmony_ci        default:
210bc2ed2b3Sopenharmony_ci            WarnLog("unknown notification ID");
211bc2ed2b3Sopenharmony_ci            return false;
212bc2ed2b3Sopenharmony_ci    }
213bc2ed2b3Sopenharmony_ci    return true;
214bc2ed2b3Sopenharmony_ci}
215bc2ed2b3Sopenharmony_ci
216bc2ed2b3Sopenharmony_cistatic bool SetTitleAndText(int notificationId,
217bc2ed2b3Sopenharmony_ci    std::shared_ptr<Notification::NotificationNormalContent> nfcContent, const std::string &name, int balance)
218bc2ed2b3Sopenharmony_ci{
219bc2ed2b3Sopenharmony_ci    if (nfcContent == nullptr) {
220bc2ed2b3Sopenharmony_ci        ErrorLog("notification normal content nullptr");
221bc2ed2b3Sopenharmony_ci        return false;
222bc2ed2b3Sopenharmony_ci    }
223bc2ed2b3Sopenharmony_ci    UpdateResourceMapByLanguage();
224bc2ed2b3Sopenharmony_ci
225bc2ed2b3Sopenharmony_ci    switch (notificationId) {
226bc2ed2b3Sopenharmony_ci        case NFC_TRANSPORT_CARD_NOTIFICATION_ID:
227bc2ed2b3Sopenharmony_ci            if (g_resourceMap.find(KEY_TRANSPORT_CARD_NTF_TITLE) != g_resourceMap.end() &&
228bc2ed2b3Sopenharmony_ci                g_resourceMap.find(KEY_TRANSPORT_CARD_NTF_TEXT) != g_resourceMap.end() &&
229bc2ed2b3Sopenharmony_ci                g_resourceMap.find(name) != g_resourceMap.end()) {
230bc2ed2b3Sopenharmony_ci                nfcContent->SetTitle(g_resourceMap[KEY_TRANSPORT_CARD_NTF_TITLE]);
231bc2ed2b3Sopenharmony_ci                nfcContent->SetText(GetTrafficCardNotificationText(name, balance));
232bc2ed2b3Sopenharmony_ci            }
233bc2ed2b3Sopenharmony_ci            break;
234bc2ed2b3Sopenharmony_ci        case NFC_WIFI_NOTIFICATION_ID:
235bc2ed2b3Sopenharmony_ci#ifdef NDEF_WIFI_ENABLED
236bc2ed2b3Sopenharmony_ci            if (g_resourceMap.find(KEY_NFC_WIFI_NTF_TITLE) != g_resourceMap.end() &&
237bc2ed2b3Sopenharmony_ci                g_resourceMap.find(KEY_NFC_WIFI_NTF_TEXT) != g_resourceMap.end()) {
238bc2ed2b3Sopenharmony_ci                nfcContent->SetTitle(g_resourceMap[KEY_NFC_WIFI_NTF_TITLE]);
239bc2ed2b3Sopenharmony_ci                nfcContent->SetText(GetWifiNotificationText(name));
240bc2ed2b3Sopenharmony_ci            }
241bc2ed2b3Sopenharmony_ci            break;
242bc2ed2b3Sopenharmony_ci#else
243bc2ed2b3Sopenharmony_ci            ErrorLog("nfc wifi notification not supported");
244bc2ed2b3Sopenharmony_ci            return false;
245bc2ed2b3Sopenharmony_ci#endif
246bc2ed2b3Sopenharmony_ci        case NFC_BT_NOTIFICATION_ID:
247bc2ed2b3Sopenharmony_ci#ifdef NDEF_BT_ENABLED
248bc2ed2b3Sopenharmony_ci            if (g_resourceMap.find(KEY_NFC_BT_NTF_TITLE) != g_resourceMap.end() &&
249bc2ed2b3Sopenharmony_ci                g_resourceMap.find(KEY_NFC_BT_NTF_TEXT) != g_resourceMap.end()) {
250bc2ed2b3Sopenharmony_ci                nfcContent->SetTitle(g_resourceMap[KEY_NFC_BT_NTF_TITLE]);
251bc2ed2b3Sopenharmony_ci                nfcContent->SetText(GetBtNotificationText(name));
252bc2ed2b3Sopenharmony_ci            }
253bc2ed2b3Sopenharmony_ci            break;
254bc2ed2b3Sopenharmony_ci#else
255bc2ed2b3Sopenharmony_ci            ErrorLog("nfc bt notification not supported");
256bc2ed2b3Sopenharmony_ci            return false;
257bc2ed2b3Sopenharmony_ci#endif
258bc2ed2b3Sopenharmony_ci        default:
259bc2ed2b3Sopenharmony_ci            return SetTitleAndTextForOtherNotificationId(notificationId, nfcContent, name, balance);
260bc2ed2b3Sopenharmony_ci    }
261bc2ed2b3Sopenharmony_ci    return true;
262bc2ed2b3Sopenharmony_ci}
263bc2ed2b3Sopenharmony_ci
264bc2ed2b3Sopenharmony_cistatic std::string GetButtonName(int notificationId)
265bc2ed2b3Sopenharmony_ci{
266bc2ed2b3Sopenharmony_ci    switch (notificationId) {
267bc2ed2b3Sopenharmony_ci        case NFC_BT_NOTIFICATION_ID:
268bc2ed2b3Sopenharmony_ci            if (g_resourceMap.find(KEY_NFC_BT_BUTTON_NAME) != g_resourceMap.end()) {
269bc2ed2b3Sopenharmony_ci                return g_resourceMap[KEY_NFC_BT_BUTTON_NAME];
270bc2ed2b3Sopenharmony_ci            }
271bc2ed2b3Sopenharmony_ci            return "";
272bc2ed2b3Sopenharmony_ci        case NFC_WIFI_NOTIFICATION_ID:
273bc2ed2b3Sopenharmony_ci            if (g_resourceMap.find(KEY_NFC_WIFI_BUTTON_NAME) != g_resourceMap.end()) {
274bc2ed2b3Sopenharmony_ci                return g_resourceMap[KEY_NFC_WIFI_BUTTON_NAME];
275bc2ed2b3Sopenharmony_ci            }
276bc2ed2b3Sopenharmony_ci            return "";
277bc2ed2b3Sopenharmony_ci        case NFC_BROWSER_NOTIFICATION_ID:
278bc2ed2b3Sopenharmony_ci            if (g_resourceMap.find(NFC_OPEN_LINK_BUTTON_NAME) != g_resourceMap.end()) {
279bc2ed2b3Sopenharmony_ci                return g_resourceMap[NFC_OPEN_LINK_BUTTON_NAME];
280bc2ed2b3Sopenharmony_ci            }
281bc2ed2b3Sopenharmony_ci            return "";
282bc2ed2b3Sopenharmony_ci        case NFC_NO_HAP_SUPPORTED_NOTIFICATION_ID:
283bc2ed2b3Sopenharmony_ci            if (g_resourceMap.find(KEY_NO_HAP_BUTTON_NAME) != g_resourceMap.end()) {
284bc2ed2b3Sopenharmony_ci                return g_resourceMap[KEY_NO_HAP_BUTTON_NAME];
285bc2ed2b3Sopenharmony_ci            }
286bc2ed2b3Sopenharmony_ci            return "";
287bc2ed2b3Sopenharmony_ci        default:
288bc2ed2b3Sopenharmony_ci            if (g_resourceMap.find(KEY_ACTION_BUTTON_NAME) != g_resourceMap.end()) {
289bc2ed2b3Sopenharmony_ci                return g_resourceMap[KEY_ACTION_BUTTON_NAME];
290bc2ed2b3Sopenharmony_ci            }
291bc2ed2b3Sopenharmony_ci            return "";
292bc2ed2b3Sopenharmony_ci    }
293bc2ed2b3Sopenharmony_ci}
294bc2ed2b3Sopenharmony_ci
295bc2ed2b3Sopenharmony_cistatic void SetActionButton(const std::string& buttonName, Notification::NotificationRequest& request)
296bc2ed2b3Sopenharmony_ci{
297bc2ed2b3Sopenharmony_ci    auto want = std::make_shared<AAFwk::Want>();
298bc2ed2b3Sopenharmony_ci    std::vector<std::shared_ptr<AAFwk::Want>> wants;
299bc2ed2b3Sopenharmony_ci    wants.push_back(want);
300bc2ed2b3Sopenharmony_ci    std::vector<AbilityRuntime::WantAgent::WantAgentConstant::Flags> flags;
301bc2ed2b3Sopenharmony_ci    flags.push_back(AbilityRuntime::WantAgent::WantAgentConstant::Flags::CONSTANT_FLAG);
302bc2ed2b3Sopenharmony_ci    AbilityRuntime::WantAgent::WantAgentInfo wantAgentInfo(
303bc2ed2b3Sopenharmony_ci        0, AbilityRuntime::WantAgent::WantAgentConstant::OperationType::UNKNOWN_TYPE,
304bc2ed2b3Sopenharmony_ci        flags, wants, nullptr
305bc2ed2b3Sopenharmony_ci    );
306bc2ed2b3Sopenharmony_ci    auto wantAgentDeal = AbilityRuntime::WantAgent::WantAgentHelper::GetWantAgent(wantAgentInfo);
307bc2ed2b3Sopenharmony_ci    std::shared_ptr<Notification::NotificationActionButton> actionButtonDeal =
308bc2ed2b3Sopenharmony_ci        Notification::NotificationActionButton::Create(nullptr, buttonName, wantAgentDeal);
309bc2ed2b3Sopenharmony_ci    if (actionButtonDeal == nullptr) {
310bc2ed2b3Sopenharmony_ci        ErrorLog("get notification actionButton nullptr");
311bc2ed2b3Sopenharmony_ci        return;
312bc2ed2b3Sopenharmony_ci    }
313bc2ed2b3Sopenharmony_ci    request.AddActionButton(actionButtonDeal);
314bc2ed2b3Sopenharmony_ci}
315bc2ed2b3Sopenharmony_ci
316bc2ed2b3Sopenharmony_cistatic int64_t GetAutoDeleteTime()
317bc2ed2b3Sopenharmony_ci{
318bc2ed2b3Sopenharmony_ci    auto now = std::chrono::system_clock::now();
319bc2ed2b3Sopenharmony_ci    auto duration = std::chrono::duration_cast<std::chrono::milliseconds>(now.time_since_epoch());
320bc2ed2b3Sopenharmony_ci    return duration.count() + NTF_AUTO_DELETE_TIME;
321bc2ed2b3Sopenharmony_ci}
322bc2ed2b3Sopenharmony_ci
323bc2ed2b3Sopenharmony_cistatic void SetBasicOption(Notification::NotificationRequest &request)
324bc2ed2b3Sopenharmony_ci{
325bc2ed2b3Sopenharmony_ci    request.SetCreatorUid(KITS::NFC_MANAGER_SYS_ABILITY_ID);
326bc2ed2b3Sopenharmony_ci    request.SetCreatorBundleName(KITS::NFC_MANAGER_SYS_ABILITY_NAME);
327bc2ed2b3Sopenharmony_ci    request.SetAutoDeletedTime(GetAutoDeleteTime());
328bc2ed2b3Sopenharmony_ci    request.SetTapDismissed(true);
329bc2ed2b3Sopenharmony_ci    request.SetSlotType(OHOS::Notification::NotificationConstant::SlotType::SOCIAL_COMMUNICATION);
330bc2ed2b3Sopenharmony_ci    request.SetNotificationControlFlags(NFC_NTF_CONTROL_FLAG);
331bc2ed2b3Sopenharmony_ci}
332bc2ed2b3Sopenharmony_ci
333bc2ed2b3Sopenharmony_civoid NfcNotification::GetPixelMap(const std::string &path)
334bc2ed2b3Sopenharmony_ci{
335bc2ed2b3Sopenharmony_ci    if (nfcIconPixelMap_ != nullptr) {
336bc2ed2b3Sopenharmony_ci        InfoLog("nfc icon pixel map already exists.");
337bc2ed2b3Sopenharmony_ci        return;
338bc2ed2b3Sopenharmony_ci    }
339bc2ed2b3Sopenharmony_ci
340bc2ed2b3Sopenharmony_ci    if (!std::filesystem::exists(path)) {
341bc2ed2b3Sopenharmony_ci        ErrorLog("nfc icon file path not exists.");
342bc2ed2b3Sopenharmony_ci        nfcIconPixelMap_ = nullptr;
343bc2ed2b3Sopenharmony_ci        return;
344bc2ed2b3Sopenharmony_ci    }
345bc2ed2b3Sopenharmony_ci    uint32_t errorCode = 0;
346bc2ed2b3Sopenharmony_ci    Media::SourceOptions opts;
347bc2ed2b3Sopenharmony_ci    opts.formatHint = "image/png";
348bc2ed2b3Sopenharmony_ci    std::unique_ptr<Media::ImageSource> imageSource = Media::ImageSource::CreateImageSource(path, opts, errorCode);
349bc2ed2b3Sopenharmony_ci    if (imageSource == nullptr) {
350bc2ed2b3Sopenharmony_ci        ErrorLog("imageSource nullptr");
351bc2ed2b3Sopenharmony_ci        nfcIconPixelMap_ = nullptr;
352bc2ed2b3Sopenharmony_ci        return;
353bc2ed2b3Sopenharmony_ci    }
354bc2ed2b3Sopenharmony_ci    Media::DecodeOptions decodeOpts;
355bc2ed2b3Sopenharmony_ci    std::unique_ptr<Media::PixelMap> pixelMap = imageSource->CreatePixelMap(decodeOpts, errorCode);
356bc2ed2b3Sopenharmony_ci    nfcIconPixelMap_ = std::move(pixelMap);
357bc2ed2b3Sopenharmony_ci}
358bc2ed2b3Sopenharmony_ci
359bc2ed2b3Sopenharmony_ciNfcNotification& NfcNotification::GetInstance()
360bc2ed2b3Sopenharmony_ci{
361bc2ed2b3Sopenharmony_ci    static NfcNotification instance;
362bc2ed2b3Sopenharmony_ci    return instance;
363bc2ed2b3Sopenharmony_ci}
364bc2ed2b3Sopenharmony_ci
365bc2ed2b3Sopenharmony_ciNfcNotification::NfcNotification()
366bc2ed2b3Sopenharmony_ci{
367bc2ed2b3Sopenharmony_ci    InfoLog("NfcNotification constructor enter.");
368bc2ed2b3Sopenharmony_ci    std::lock_guard<std::mutex> lock(mutex_);
369bc2ed2b3Sopenharmony_ci    // only need to subscribe notification once
370bc2ed2b3Sopenharmony_ci    int result = Notification::NotificationHelper::SubscribeNotification(*g_notificationSubscriber);
371bc2ed2b3Sopenharmony_ci    if (result != ERR_OK) {
372bc2ed2b3Sopenharmony_ci        ErrorLog("fail to subscribe notification");
373bc2ed2b3Sopenharmony_ci    }
374bc2ed2b3Sopenharmony_ci    UpdateResourceMapByLanguage();
375bc2ed2b3Sopenharmony_ci    // initialize the vector with the length of (NFC_NTF_END - NFC_TAG_DEFAULT_NTF_ID)
376bc2ed2b3Sopenharmony_ci    tagNtfCountVec_.resize(NFC_NTF_END - NFC_TAG_DEFAULT_NTF_ID);
377bc2ed2b3Sopenharmony_ci}
378bc2ed2b3Sopenharmony_ci
379bc2ed2b3Sopenharmony_ciNfcNotification::~NfcNotification()
380bc2ed2b3Sopenharmony_ci{
381bc2ed2b3Sopenharmony_ci    InfoLog("NfcNotification destructor enter.");
382bc2ed2b3Sopenharmony_ci    // no operation to unsubscribe notification
383bc2ed2b3Sopenharmony_ci}
384bc2ed2b3Sopenharmony_ci
385bc2ed2b3Sopenharmony_civoid NfcNotification::PublishNfcNotification(int notificationId, const std::string &name, int balance)
386bc2ed2b3Sopenharmony_ci{
387bc2ed2b3Sopenharmony_ci    if (notificationId >= NFC_NTF_END || notificationId < NFC_TAG_DEFAULT_NTF_ID) {
388bc2ed2b3Sopenharmony_ci        ErrorLog("invalid notification id.");
389bc2ed2b3Sopenharmony_ci        return;
390bc2ed2b3Sopenharmony_ci    }
391bc2ed2b3Sopenharmony_ci    std::shared_ptr<Notification::NotificationNormalContent> nfcContent =
392bc2ed2b3Sopenharmony_ci        std::make_shared<Notification::NotificationNormalContent>();
393bc2ed2b3Sopenharmony_ci    if (nfcContent == nullptr) {
394bc2ed2b3Sopenharmony_ci        ErrorLog("get notification normal content nullptr");
395bc2ed2b3Sopenharmony_ci        return;
396bc2ed2b3Sopenharmony_ci    }
397bc2ed2b3Sopenharmony_ci    std::lock_guard<std::mutex> lock(mutex_);
398bc2ed2b3Sopenharmony_ci    Notification::NotificationBundleOption bundle(KITS::NFC_MANAGER_SYS_ABILITY_NAME, KITS::NFC_MANAGER_SYS_ABILITY_ID);
399bc2ed2b3Sopenharmony_ci    int lastNtfId = (tagNtfCountVec_[notificationId - NFC_TAG_DEFAULT_NTF_ID]++) * NTF_COUNT_CONSTANT + notificationId;
400bc2ed2b3Sopenharmony_ci    if (tagNtfCountVec_[notificationId - NFC_TAG_DEFAULT_NTF_ID] >= NFC_MAX_NTF_COUNT) {
401bc2ed2b3Sopenharmony_ci        tagNtfCountVec_[notificationId - NFC_TAG_DEFAULT_NTF_ID] = 0;
402bc2ed2b3Sopenharmony_ci    }
403bc2ed2b3Sopenharmony_ci    int currentNtfId = (tagNtfCountVec_[notificationId - NFC_TAG_DEFAULT_NTF_ID]) * NTF_COUNT_CONSTANT + notificationId;
404bc2ed2b3Sopenharmony_ci    int ret = Notification::NotificationHelper::CancelAsBundle(bundle, lastNtfId);
405bc2ed2b3Sopenharmony_ci    // ret value 67108880 represents the notification does not exist
406bc2ed2b3Sopenharmony_ci    InfoLog("Cancel ntf result[%{public}d], last id[%{public}d], current id[%{public}d]", ret, lastNtfId, currentNtfId);
407bc2ed2b3Sopenharmony_ci
408bc2ed2b3Sopenharmony_ci    if (!SetTitleAndText(notificationId, nfcContent, name, balance)) {
409bc2ed2b3Sopenharmony_ci        ErrorLog("error setting title and text");
410bc2ed2b3Sopenharmony_ci        return;
411bc2ed2b3Sopenharmony_ci    }
412bc2ed2b3Sopenharmony_ci
413bc2ed2b3Sopenharmony_ci    std::shared_ptr<Notification::NotificationContent> content =
414bc2ed2b3Sopenharmony_ci        std::make_shared<Notification::NotificationContent>(nfcContent);
415bc2ed2b3Sopenharmony_ci    if (content == nullptr) {
416bc2ed2b3Sopenharmony_ci        ErrorLog("get notification content nullptr");
417bc2ed2b3Sopenharmony_ci        return;
418bc2ed2b3Sopenharmony_ci    }
419bc2ed2b3Sopenharmony_ci
420bc2ed2b3Sopenharmony_ci    Notification::NotificationRequest request;
421bc2ed2b3Sopenharmony_ci    SetBasicOption(request);
422bc2ed2b3Sopenharmony_ci    request.SetNotificationId(currentNtfId);
423bc2ed2b3Sopenharmony_ci    request.SetContent(content);
424bc2ed2b3Sopenharmony_ci
425bc2ed2b3Sopenharmony_ci    GetPixelMap(NFC_ICON_PATH);
426bc2ed2b3Sopenharmony_ci    if (nfcIconPixelMap_ != nullptr) {
427bc2ed2b3Sopenharmony_ci        request.SetLittleIcon(nfcIconPixelMap_);
428bc2ed2b3Sopenharmony_ci        request.SetBadgeIconStyle(Notification::NotificationRequest::BadgeStyle::LITTLE);
429bc2ed2b3Sopenharmony_ci    }
430bc2ed2b3Sopenharmony_ci
431bc2ed2b3Sopenharmony_ci    std::string buttonName = GetButtonName(notificationId);
432bc2ed2b3Sopenharmony_ci    if (!buttonName.empty()) {
433bc2ed2b3Sopenharmony_ci        SetActionButton(buttonName, request);
434bc2ed2b3Sopenharmony_ci    }
435bc2ed2b3Sopenharmony_ci
436bc2ed2b3Sopenharmony_ci    Notification::NotificationHelper::SetNotificationSlotFlagsAsBundle(bundle, NFC_SLOT_CONTROL_FLAG);
437bc2ed2b3Sopenharmony_ci    ret = Notification::NotificationHelper::PublishNotification(request);
438bc2ed2b3Sopenharmony_ci    InfoLog("NFC service publish notification result = %{public}d", ret);
439bc2ed2b3Sopenharmony_ci}
440bc2ed2b3Sopenharmony_ci
441bc2ed2b3Sopenharmony_civoid NfcNotification::RegNotificationCallback(NfcNtfCallback callback)
442bc2ed2b3Sopenharmony_ci{
443bc2ed2b3Sopenharmony_ci    std::lock_guard<std::mutex> lock(g_callbackMutex);
444bc2ed2b3Sopenharmony_ci    g_ntfCallback = callback;
445bc2ed2b3Sopenharmony_ci}
446bc2ed2b3Sopenharmony_ci}  // namespace TAG
447bc2ed2b3Sopenharmony_ci}  // namespace NFC
448bc2ed2b3Sopenharmony_ci}  // namespace OHOS
449bc2ed2b3Sopenharmony_ci
450bc2ed2b3Sopenharmony_civoid RegNotificationCallback(NfcNtfCallback callback)
451bc2ed2b3Sopenharmony_ci{
452bc2ed2b3Sopenharmony_ci    OHOS::NFC::TAG::NfcNotification::GetInstance().RegNotificationCallback(callback);
453bc2ed2b3Sopenharmony_ci}
454bc2ed2b3Sopenharmony_ci
455bc2ed2b3Sopenharmony_civoid PublishNfcNotification(int notificationId, const std::string &name, int balance)
456bc2ed2b3Sopenharmony_ci{
457bc2ed2b3Sopenharmony_ci    InfoLog("Publishing nfc tag notification, id [%{public}d]", notificationId);
458bc2ed2b3Sopenharmony_ci    OHOS::NFC::TAG::NfcNotification::GetInstance().PublishNfcNotification(notificationId, name, balance);
459bc2ed2b3Sopenharmony_ci}