1 /*
2 * Copyright (c) 2021-2024 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 "napi_display_badge.h"
17
18 #include "ans_inner_errors.h"
19 #include "display_badge.h"
20
21 namespace OHOS {
22 namespace NotificationNapi {
23 const int32_t SET_BADGE_NUMBER_MAX_PARA = 2;
24 const int32_t SET_BADGE_NUMBER_MIN_PARA = 1;
25 const int32_t SET_BADGE_NUMBER_BY_BUNDLE_PARA = 2;
26
NapiDisplayBadge(napi_env env,napi_callback_info info)27 napi_value NapiDisplayBadge(napi_env env, napi_callback_info info)
28 {
29 ANS_LOGD("called");
30 EnableBadgeParams params {};
31 if (ParseParameters(env, info, params) == nullptr) {
32 Common::NapiThrow(env, ERROR_PARAM_INVALID);
33 return Common::NapiGetUndefined(env);
34 }
35
36 AsyncCallbackInfoEnableBadge *asynccallbackinfo =
37 new (std::nothrow) AsyncCallbackInfoEnableBadge {.env = env, .asyncWork = nullptr, .params = params};
38 if (!asynccallbackinfo) {
39 Common::NapiThrow(env, ERROR_INTERNAL_ERROR);
40 return Common::JSParaError(env, params.callback);
41 }
42 napi_value promise = nullptr;
43 Common::PaddingCallbackPromiseInfo(env, params.callback, asynccallbackinfo->info, promise);
44
45 napi_value resourceName = nullptr;
46 napi_create_string_latin1(env, "DisplayBadge", NAPI_AUTO_LENGTH, &resourceName);
47 // Asynchronous function call
48 napi_create_async_work(env,
49 nullptr,
50 resourceName,
51 [](napi_env env, void *data) {
52 ANS_LOGD("NapiDisplayBadge work excute.");
53 AsyncCallbackInfoEnableBadge *asynccallbackinfo = static_cast<AsyncCallbackInfoEnableBadge *>(data);
54 if (asynccallbackinfo) {
55 ANS_LOGI("bundle=%{public}s uid=%{public}d enable=%{public}d",
56 asynccallbackinfo->params.option.GetBundleName().c_str(),
57 asynccallbackinfo->params.option.GetUid(),
58 asynccallbackinfo->params.enable);
59 asynccallbackinfo->info.errorCode = NotificationHelper::SetShowBadgeEnabledForBundle(
60 asynccallbackinfo->params.option, asynccallbackinfo->params.enable);
61 ANS_LOGI("asynccallbackinfo->info.errorCode = %{public}d", asynccallbackinfo->info.errorCode);
62 }
63 },
64 [](napi_env env, napi_status status, void *data) {
65 ANS_LOGD("NapiDisplayBadge work complete.");
66 AsyncCallbackInfoEnableBadge *asynccallbackinfo = static_cast<AsyncCallbackInfoEnableBadge *>(data);
67 if (asynccallbackinfo) {
68 Common::CreateReturnValue(env, asynccallbackinfo->info, Common::NapiGetNull(env));
69 if (asynccallbackinfo->info.callback != nullptr) {
70 ANS_LOGD("Delete napiDisplayBadge callback reference.");
71 napi_delete_reference(env, asynccallbackinfo->info.callback);
72 }
73 napi_delete_async_work(env, asynccallbackinfo->asyncWork);
74 delete asynccallbackinfo;
75 asynccallbackinfo = nullptr;
76 }
77 ANS_LOGD("NapiDisplayBadge work complete end.");
78 },
79 (void *)asynccallbackinfo,
80 &asynccallbackinfo->asyncWork);
81
82 bool isCallback = asynccallbackinfo->info.isCallback;
83 napi_queue_async_work_with_qos(env, asynccallbackinfo->asyncWork, napi_qos_user_initiated);
84
85 if (isCallback) {
86 ANS_LOGD("null isCallback");
87 return Common::NapiGetNull(env);
88 } else {
89 return promise;
90 }
91 }
92
AsyncCompleteCallbackNapiIsBadgeDisplayed(napi_env env,napi_status status,void * data)93 void AsyncCompleteCallbackNapiIsBadgeDisplayed(napi_env env, napi_status status, void *data)
94 {
95 ANS_LOGD("called");
96 if (!data) {
97 ANS_LOGE("Invalid async callback data");
98 return;
99 }
100 AsyncCallbackInfoIsDisplayBadge *asynccallbackinfo = static_cast<AsyncCallbackInfoIsDisplayBadge *>(data);
101 if (asynccallbackinfo) {
102 napi_value result = nullptr;
103 napi_get_boolean(env, asynccallbackinfo->enabled, &result);
104 Common::CreateReturnValue(env, asynccallbackinfo->info, result);
105 if (asynccallbackinfo->info.callback != nullptr) {
106 napi_delete_reference(env, asynccallbackinfo->info.callback);
107 }
108 napi_delete_async_work(env, asynccallbackinfo->asyncWork);
109 delete asynccallbackinfo;
110 asynccallbackinfo = nullptr;
111 }
112 }
113
NapiIsBadgeDisplayed(napi_env env,napi_callback_info info)114 napi_value NapiIsBadgeDisplayed(napi_env env, napi_callback_info info)
115 {
116 ANS_LOGD("called");
117 IsDisplayBadgeParams params {};
118 if (ParseParameters(env, info, params) == nullptr) {
119 ANS_LOGE("Failed to parse params!");
120 Common::NapiThrow(env, ERROR_PARAM_INVALID);
121 return Common::NapiGetUndefined(env);
122 }
123
124 AsyncCallbackInfoIsDisplayBadge *asynccallbackinfo =
125 new (std::nothrow) AsyncCallbackInfoIsDisplayBadge {.env = env, .asyncWork = nullptr, .params = params};
126 if (!asynccallbackinfo) {
127 Common::NapiThrow(env, ERROR_INTERNAL_ERROR);
128 return Common::JSParaError(env, params.callback);
129 }
130 napi_value promise = nullptr;
131 Common::PaddingCallbackPromiseInfo(env, params.callback, asynccallbackinfo->info, promise);
132
133 napi_value resourceName = nullptr;
134 napi_create_string_latin1(env, "IsBadgeDisplayed", NAPI_AUTO_LENGTH, &resourceName);
135 // Asynchronous function call
136 napi_create_async_work(env,
137 nullptr,
138 resourceName,
139 [](napi_env env, void *data) {
140 ANS_LOGD("NapiIsBadgeDisplayed work excute.");
141 AsyncCallbackInfoIsDisplayBadge *asynccallbackinfo = static_cast<AsyncCallbackInfoIsDisplayBadge *>(data);
142 if (asynccallbackinfo) {
143 if (asynccallbackinfo->params.hasBundleOption) {
144 ANS_LOGI("bundle=%{public}s uid=%{public}d",
145 asynccallbackinfo->params.option.GetBundleName().c_str(),
146 asynccallbackinfo->params.option.GetUid());
147 asynccallbackinfo->info.errorCode = NotificationHelper::GetShowBadgeEnabledForBundle(
148 asynccallbackinfo->params.option, asynccallbackinfo->enabled);
149 } else {
150 asynccallbackinfo->info.errorCode = NotificationHelper::GetShowBadgeEnabled(
151 asynccallbackinfo->enabled);
152 }
153 ANS_LOGI("errorCode = %{public}d, enabled = %{public}d",
154 asynccallbackinfo->info.errorCode, asynccallbackinfo->enabled);
155 }
156 },
157 AsyncCompleteCallbackNapiIsBadgeDisplayed,
158 (void *)asynccallbackinfo,
159 &asynccallbackinfo->asyncWork);
160
161 bool isCallback = asynccallbackinfo->info.isCallback;
162 napi_queue_async_work_with_qos(env, asynccallbackinfo->asyncWork, napi_qos_user_initiated);
163
164 if (isCallback) {
165 ANS_LOGD("null isCallback");
166 return Common::NapiGetNull(env);
167 } else {
168 return promise;
169 }
170 }
171
ParseParameters(const napi_env & env,const napi_callback_info & info,SetBadgeNumberParams & params)172 napi_value ParseParameters(const napi_env &env, const napi_callback_info &info, SetBadgeNumberParams ¶ms)
173 {
174 ANS_LOGD("called");
175
176 size_t argc = SET_BADGE_NUMBER_MAX_PARA;
177 napi_value argv[SET_BADGE_NUMBER_MAX_PARA] = {nullptr};
178 napi_value thisVar = nullptr;
179 NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, NULL));
180 if (argc < SET_BADGE_NUMBER_MIN_PARA) {
181 ANS_LOGW("Wrong number of arguments.");
182 Common::NapiThrow(env, ERROR_PARAM_INVALID, MANDATORY_PARAMETER_ARE_LEFT_UNSPECIFIED);
183 return nullptr;
184 }
185
186 // argv[0]: badgeNumber or bundleOption
187 napi_valuetype valuetype = napi_undefined;
188 NAPI_CALL(env, napi_typeof(env, argv[PARAM0], &valuetype));
189 // case1: setBadgeNumberByBundle(bundleOption, badgeNumber)
190 if (valuetype == napi_object) {
191 if (argc != SET_BADGE_NUMBER_BY_BUNDLE_PARA) {
192 ANS_LOGE("Wrong number of arguments. Expect exactly two.");
193 std::string msg = "Mandatory parameters are left unspecified. Expect exactly two.";
194 Common::NapiThrow(env, ERROR_PARAM_INVALID, msg);
195 return nullptr;
196 }
197 Common::GetBundleOption(env, argv[PARAM0], params.option);
198 // argv[1]: badgeNumber
199 NAPI_CALL(env, napi_typeof(env, argv[PARAM1], &valuetype));
200 if (valuetype != napi_number) {
201 ANS_LOGE("Wrong argument type. Number expected.");
202 std::string msg = "Incorrect parameter types.The type of param must be number.";
203 Common::NapiThrow(env, ERROR_PARAM_INVALID, msg);
204 return nullptr;
205 }
206 napi_get_value_int32(env, argv[PARAM1], ¶ms.badgeNumber);
207 return Common::NapiGetNull(env);
208 }
209 // case2: setBadgeNumber(badgeNumber)
210 if (valuetype != napi_number) {
211 ANS_LOGW("Wrong argument type. Number expected.");
212 std::string msg = "Incorrect parameter types.The type of param must be object.";
213 Common::NapiThrow(env, ERROR_PARAM_INVALID, msg);
214 return nullptr;
215 }
216 napi_get_value_int32(env, argv[PARAM0], ¶ms.badgeNumber);
217
218 // argv[1]:callback
219 if (argc >= SET_BADGE_NUMBER_MAX_PARA) {
220 NAPI_CALL(env, napi_typeof(env, argv[PARAM1], &valuetype));
221 if (valuetype != napi_function) {
222 ANS_LOGW("Callback is not function excute promise.");
223 return Common::NapiGetNull(env);
224 }
225 napi_create_reference(env, argv[PARAM1], 1, ¶ms.callback);
226 }
227
228 return Common::NapiGetNull(env);
229 }
230
AsyncCompleteCallbackNapiSetBadgeNumber(napi_env env,napi_status status,void * data)231 void AsyncCompleteCallbackNapiSetBadgeNumber(napi_env env, napi_status status, void *data)
232 {
233 ANS_LOGD("called");
234 if (!data) {
235 ANS_LOGE("Invalid async callback data");
236 return;
237 }
238 AsyncCallbackSetBadgeNumber *asynccallbackinfo = static_cast<AsyncCallbackSetBadgeNumber *>(data);
239 Common::CreateReturnValue(env, asynccallbackinfo->info, Common::NapiGetNull(env));
240 if (asynccallbackinfo->info.callback != nullptr) {
241 napi_delete_reference(env, asynccallbackinfo->info.callback);
242 }
243 napi_delete_async_work(env, asynccallbackinfo->asyncWork);
244 delete asynccallbackinfo;
245 asynccallbackinfo = nullptr;
246 }
247
NapiSetBadgeNumber(napi_env env,napi_callback_info info)248 napi_value NapiSetBadgeNumber(napi_env env, napi_callback_info info)
249 {
250 ANS_LOGD("called");
251 SetBadgeNumberParams params {};
252 if (ParseParameters(env, info, params) == nullptr) {
253 Common::NapiThrow(env, ERROR_PARAM_INVALID);
254 return Common::NapiGetUndefined(env);
255 }
256
257 AsyncCallbackSetBadgeNumber *asynccallbackinfo =
258 new (std::nothrow) AsyncCallbackSetBadgeNumber {.env = env, .asyncWork = nullptr, .params = params};
259 if (!asynccallbackinfo) {
260 Common::NapiThrow(env, ERROR_PARAM_INVALID);
261 return Common::NapiGetUndefined(env);
262 }
263 napi_value promise = nullptr;
264 Common::PaddingCallbackPromiseInfo(env, params.callback, asynccallbackinfo->info, promise);
265
266 napi_value resourceName = nullptr;
267 napi_create_string_latin1(env, "setBadgeNumber", NAPI_AUTO_LENGTH, &resourceName);
268 // Asynchronous function call
269 napi_create_async_work(env,
270 nullptr,
271 resourceName,
272 [](napi_env env, void *data) {
273 ANS_LOGD("NapiSetBadgeNumber work excute.");
274 AsyncCallbackSetBadgeNumber *asynccallbackinfo = static_cast<AsyncCallbackSetBadgeNumber *>(data);
275 if (asynccallbackinfo) {
276 ANS_LOGI("badgeNumber: %{public}d", asynccallbackinfo->params.badgeNumber);
277 std::string instanceKey = Common::GetAppInstanceKey();
278 asynccallbackinfo->info.errorCode = NotificationHelper::SetBadgeNumber(
279 asynccallbackinfo->params.badgeNumber, instanceKey);
280 }
281 },
282 AsyncCompleteCallbackNapiSetBadgeNumber,
283 (void *)asynccallbackinfo,
284 &asynccallbackinfo->asyncWork);
285
286 bool isCallback = asynccallbackinfo->info.isCallback;
287 napi_queue_async_work_with_qos(env, asynccallbackinfo->asyncWork, napi_qos_user_initiated);
288
289 if (isCallback) {
290 ANS_LOGD("null isCallback");
291 return Common::NapiGetNull(env);
292 } else {
293 return promise;
294 }
295 }
296
NapiSetBadgeNumberByBundle(napi_env env,napi_callback_info info)297 napi_value NapiSetBadgeNumberByBundle(napi_env env, napi_callback_info info)
298 {
299 ANS_LOGD("called");
300 SetBadgeNumberParams params {};
301 if (ParseParameters(env, info, params) == nullptr) {
302 Common::NapiThrow(env, ERROR_PARAM_INVALID);
303 return Common::NapiGetUndefined(env);
304 }
305
306 AsyncCallbackSetBadgeNumber *asyncCallbackInfo =
307 new (std::nothrow) AsyncCallbackSetBadgeNumber {.env = env, .asyncWork = nullptr, .params = params};
308 if (asyncCallbackInfo == nullptr) {
309 Common::NapiThrow(env, ERROR_PARAM_INVALID, MANDATORY_PARAMETER_ARE_LEFT_UNSPECIFIED);
310 return Common::NapiGetUndefined(env);
311 }
312 napi_value promise = nullptr;
313 Common::PaddingCallbackPromiseInfo(env, params.callback, asyncCallbackInfo->info, promise);
314
315 napi_value resourceName = nullptr;
316 napi_create_string_latin1(env, "setBadgeNumberByBundle", NAPI_AUTO_LENGTH, &resourceName);
317 // Asynchronous function call
318 napi_create_async_work(env,
319 nullptr,
320 resourceName,
321 [](napi_env env, void *data) {
322 ANS_LOGD("Napi set badge number by bundle work execute.");
323 AsyncCallbackSetBadgeNumber *asyncCallbackInfo = static_cast<AsyncCallbackSetBadgeNumber *>(data);
324 if (asyncCallbackInfo) {
325 ANS_LOGI("bundle=%{public}s uid=%{public}d badge=%{public}d",
326 asyncCallbackInfo->params.option.GetBundleName().c_str(),
327 asyncCallbackInfo->params.option.GetUid(),
328 asyncCallbackInfo->params.badgeNumber);
329 asyncCallbackInfo->info.errorCode = NotificationHelper::SetBadgeNumberByBundle(
330 asyncCallbackInfo->params.option, asyncCallbackInfo->params.badgeNumber);
331 }
332 },
333 AsyncCompleteCallbackNapiSetBadgeNumber,
334 (void *)asyncCallbackInfo,
335 &asyncCallbackInfo->asyncWork);
336
337 bool isCallback = asyncCallbackInfo->info.isCallback;
338 napi_queue_async_work_with_qos(env, asyncCallbackInfo->asyncWork, napi_qos_user_initiated);
339
340 if (isCallback) {
341 ANS_LOGD("null isCallback");
342 return Common::NapiGetNull(env);
343 } else {
344 return promise;
345 }
346 }
347 } // namespace NotificationNapi
348 } // namespace OHOS
349