• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021 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 "subscribe.h"
17 
18 #include <mutex>
19 #include <uv.h>
20 
21 namespace OHOS {
22 namespace NotificationNapi {
23 const int32_t SUBSRIBE_MAX_PARA = 3;
24 const int32_t NO_DELETE_REASON = -1;
25 const std::string CONSUME = "onConsume";
26 const std::string CANCEL = "onCancel";
27 const std::string UPDATE = "onUpdate";
28 const std::string CONNECTED = "onConnect";
29 const std::string DIS_CONNECTED = "onDisconnect";
30 const std::string DIE = "onDestroy";
31 const std::string DISTURB_MODE_CHANGE = "onDisturbModeChange";
32 const std::string DISTURB_DATE_CHANGE = "onDoNotDisturbDateChange";
33 const std::string ENABLE_NOTIFICATION_CHANGED = "OnEnabledNotificationChanged";
34 
35 struct NotificationReceiveDataWorker {
36     napi_env env = nullptr;
37     napi_ref ref = nullptr;
38     std::shared_ptr<OHOS::Notification::Notification> request;
39     std::shared_ptr<NotificationSortingMap> sortingMap;
40     NotificationDoNotDisturbDate date;
41     EnabledNotificationCallbackData callbackData;
42     int32_t deleteReason = 0;
43     int32_t result = 0;
44     int32_t disturbMode = 0;
45     SubscriberInstance *subscriber = nullptr;
46 };
47 
SetSubscribeCallbackData(const napi_env & env,const std::shared_ptr<OHOS::Notification::Notification> & request,const std::shared_ptr<NotificationSortingMap> & sortingMap,int32_t deleteReason,napi_value & result)48 napi_value SetSubscribeCallbackData(const napi_env &env,
49     const std::shared_ptr<OHOS::Notification::Notification> &request,
50     const std::shared_ptr<NotificationSortingMap> &sortingMap, int32_t deleteReason, napi_value &result)
51 {
52     ANS_LOGI("enter");
53     if (request == nullptr) {
54         ANS_LOGE("request is null");
55         return Common::NapiGetBoolean(env, false);
56     }
57 
58     if (sortingMap == nullptr) {
59         ANS_LOGE("sortingMap is null");
60         return Common::NapiGetBoolean(env, false);
61     }
62 
63     // request: NotificationRequest
64     napi_value requestResult = nullptr;
65     napi_create_object(env, &requestResult);
66     if (!Common::SetNotification(env, request.get(), requestResult)) {
67         ANS_LOGE("SetNotification call failed");
68         return Common::NapiGetBoolean(env, false);
69     }
70     napi_set_named_property(env, result, "request", requestResult);
71 
72     // sortingMap?: NotificationSortingMap
73     napi_value sortingMapResult = nullptr;
74     napi_create_object(env, &sortingMapResult);
75     if (!Common::SetNotificationSortingMap(env, sortingMap, sortingMapResult)) {
76         ANS_LOGE("SetNotificationSortingMap call failed");
77         return Common::NapiGetBoolean(env, false);
78     }
79     napi_set_named_property(env, result, "sortingMap", sortingMapResult);
80 
81     // reason?: number
82     if (deleteReason != NO_DELETE_REASON) {
83         napi_value value = nullptr;
84         int32_t outReason = 0;
85         if (!Common::ReasonCToJS(deleteReason, outReason)) {
86             return Common::NapiGetBoolean(env, false);
87         }
88         napi_create_int32(env, outReason, &value);
89         napi_set_named_property(env, result, "reason", value);
90     }
91 
92     // sound?: string
93     napi_value soundResult = nullptr;
94     std::string sound;
95     if (request->EnableSound()) {
96         sound = request->GetSound().ToString();
97     }
98     napi_create_string_utf8(env, sound.c_str(), NAPI_AUTO_LENGTH, &soundResult);
99     napi_set_named_property(env, result, "sound", soundResult);
100 
101     // vibrationValues?: Array<number>
102     napi_value arr = nullptr;
103     napi_create_array(env, &arr);
104     if (request->EnableVibrate()) {
105         uint32_t count = 0;
106         for (auto vec : request->GetVibrationStyle()) {
107             napi_value nVibrationValue = nullptr;
108             napi_create_int64(env, vec, &nVibrationValue);
109             napi_set_element(env, arr, count, nVibrationValue);
110             count++;
111         }
112     }
113     napi_set_named_property(env, result, "vibrationValues", arr);
114 
115     return Common::NapiGetBoolean(env, true);
116 }
117 
SubscriberInstance()118 SubscriberInstance::SubscriberInstance()
119 {}
120 
~SubscriberInstance()121 SubscriberInstance::~SubscriberInstance()
122 {
123     if (canceCallbackInfo_.ref != nullptr) {
124         napi_delete_reference(canceCallbackInfo_.env, canceCallbackInfo_.ref);
125     }
126     if (consumeCallbackInfo_.ref != nullptr) {
127         napi_delete_reference(consumeCallbackInfo_.env, consumeCallbackInfo_.ref);
128     }
129     if (updateCallbackInfo_.ref != nullptr) {
130         napi_delete_reference(updateCallbackInfo_.env, updateCallbackInfo_.ref);
131     }
132     if (subscribeCallbackInfo_.ref != nullptr) {
133         napi_delete_reference(subscribeCallbackInfo_.env, subscribeCallbackInfo_.ref);
134     }
135     if (unsubscribeCallbackInfo_.ref != nullptr) {
136         napi_delete_reference(unsubscribeCallbackInfo_.env, unsubscribeCallbackInfo_.ref);
137     }
138     if (dieCallbackInfo_.ref != nullptr) {
139         napi_delete_reference(dieCallbackInfo_.env, dieCallbackInfo_.ref);
140     }
141     if (disturbModeCallbackInfo_.ref != nullptr) {
142         napi_delete_reference(disturbModeCallbackInfo_.env, disturbModeCallbackInfo_.ref);
143     }
144     if (enabledNotificationCallbackInfo_.ref != nullptr) {
145         napi_delete_reference(enabledNotificationCallbackInfo_.env, enabledNotificationCallbackInfo_.ref);
146     }
147 }
148 
UvQueueWorkOnCanceled(uv_work_t * work,int status)149 void UvQueueWorkOnCanceled(uv_work_t *work, int status)
150 {
151     ANS_LOGI("OnCanceled uv_work_t start");
152 
153     if (work == nullptr) {
154         ANS_LOGE("work is null");
155         return;
156     }
157 
158     auto dataWorkerData = reinterpret_cast<NotificationReceiveDataWorker *>(work->data);
159     if (dataWorkerData == nullptr) {
160         ANS_LOGE("dataWorkerData is null");
161         delete work;
162         work = nullptr;
163         return;
164     }
165     napi_value result = nullptr;
166     napi_create_object(dataWorkerData->env, &result);
167     if (!SetSubscribeCallbackData(dataWorkerData->env,
168         dataWorkerData->request,
169         dataWorkerData->sortingMap,
170         dataWorkerData->deleteReason,
171         result)) {
172         ANS_LOGE("Failed to convert data to JS");
173     } else {
174         Common::SetCallback(dataWorkerData->env, dataWorkerData->ref, result);
175     }
176 
177     delete dataWorkerData;
178     dataWorkerData = nullptr;
179     delete work;
180 }
181 
OnCanceled(const std::shared_ptr<OHOS::Notification::Notification> & request,const std::shared_ptr<NotificationSortingMap> & sortingMap,int32_t deleteReason)182 void SubscriberInstance::OnCanceled(const std::shared_ptr<OHOS::Notification::Notification> &request,
183     const std::shared_ptr<NotificationSortingMap> &sortingMap, int32_t deleteReason)
184 {
185     ANS_LOGI("enter");
186 
187     if (canceCallbackInfo_.ref == nullptr) {
188         ANS_LOGI("cancel callback unset");
189         return;
190     }
191 
192     if (request == nullptr) {
193         ANS_LOGE("request is null");
194         return;
195     }
196 
197     if (sortingMap == nullptr) {
198         ANS_LOGE("sortingMap is null");
199         return;
200     }
201     ANS_LOGI("OnCanceled NotificationId = %{public}d", request->GetNotificationRequest().GetNotificationId());
202     ANS_LOGI("OnCanceled sortingMap size = %{public}zu", sortingMap->GetKey().size());
203     ANS_LOGI("OnCanceled deleteReason = %{public}d", deleteReason);
204 
205     uv_loop_s *loop = nullptr;
206     napi_get_uv_event_loop(canceCallbackInfo_.env, &loop);
207     if (loop == nullptr) {
208         ANS_LOGE("loop instance is nullptr");
209         return;
210     }
211 
212     NotificationReceiveDataWorker *dataWorker = new (std::nothrow) NotificationReceiveDataWorker();
213     if (dataWorker == nullptr) {
214         ANS_LOGE("new dataWorker failed");
215         return;
216     }
217 
218     dataWorker->request = request;
219     dataWorker->sortingMap = sortingMap;
220     dataWorker->deleteReason = deleteReason;
221     dataWorker->env = canceCallbackInfo_.env;
222     dataWorker->ref = canceCallbackInfo_.ref;
223 
224     uv_work_t *work = new (std::nothrow) uv_work_t;
225     if (work == nullptr) {
226         ANS_LOGE("new work failed");
227         delete dataWorker;
228         dataWorker = nullptr;
229         return;
230     }
231 
232     work->data = reinterpret_cast<void *>(dataWorker);
233 
234     int ret = uv_queue_work(loop, work, [](uv_work_t *work) {}, UvQueueWorkOnCanceled);
235     if (ret != 0) {
236         delete dataWorker;
237         dataWorker = nullptr;
238         delete work;
239         work = nullptr;
240     }
241 }
242 
OnConsumed(const std::shared_ptr<OHOS::Notification::Notification> & request)243 void SubscriberInstance::OnConsumed(const std::shared_ptr<OHOS::Notification::Notification> &request)
244 {}
245 
UvQueueWorkOnConsumed(uv_work_t * work,int status)246 void UvQueueWorkOnConsumed(uv_work_t *work, int status)
247 {
248     ANS_LOGI("OnConsumed uv_work_t start");
249 
250     if (work == nullptr) {
251         ANS_LOGE("work is null");
252         return;
253     }
254 
255     auto dataWorkerData = reinterpret_cast<NotificationReceiveDataWorker *>(work->data);
256     if (dataWorkerData == nullptr) {
257         ANS_LOGE("dataWorkerData is null");
258         delete work;
259         work = nullptr;
260         return;
261     }
262     napi_value result = nullptr;
263     napi_create_object(dataWorkerData->env, &result);
264     if (!SetSubscribeCallbackData(dataWorkerData->env,
265         dataWorkerData->request,
266         dataWorkerData->sortingMap,
267         NO_DELETE_REASON,
268         result)) {
269         ANS_LOGE("Failed to convert data to JS");
270     } else {
271         Common::SetCallback(dataWorkerData->env, dataWorkerData->ref, result);
272     }
273 
274     delete dataWorkerData;
275     dataWorkerData = nullptr;
276     delete work;
277 }
278 
OnConsumed(const std::shared_ptr<OHOS::Notification::Notification> & request,const std::shared_ptr<NotificationSortingMap> & sortingMap)279 void SubscriberInstance::OnConsumed(const std::shared_ptr<OHOS::Notification::Notification> &request,
280     const std::shared_ptr<NotificationSortingMap> &sortingMap)
281 {
282     ANS_LOGI("enter");
283 
284     if (consumeCallbackInfo_.ref == nullptr) {
285         ANS_LOGI("consume callback unset");
286         return;
287     }
288 
289     if (request == nullptr) {
290         ANS_LOGE("request is null");
291         return;
292     }
293 
294     if (sortingMap == nullptr) {
295         ANS_LOGE("sortingMap is null");
296         return;
297     }
298     ANS_LOGI("OnConsumed Notification key = %{public}s, sortingMap size = %{public}zu",
299         request->GetKey().c_str(), sortingMap->GetKey().size());
300 
301     uv_loop_s *loop = nullptr;
302     napi_get_uv_event_loop(consumeCallbackInfo_.env, &loop);
303     if (loop == nullptr) {
304         ANS_LOGE("loop instance is nullptr");
305         return;
306     }
307 
308     NotificationReceiveDataWorker *dataWorker = new (std::nothrow) NotificationReceiveDataWorker();
309     if (dataWorker == nullptr) {
310         ANS_LOGE("new dataWorker failed");
311         return;
312     }
313 
314     dataWorker->request = request;
315     dataWorker->sortingMap = sortingMap;
316     dataWorker->env = consumeCallbackInfo_.env;
317     dataWorker->ref = consumeCallbackInfo_.ref;
318 
319     uv_work_t *work = new (std::nothrow) uv_work_t;
320     if (work == nullptr) {
321         ANS_LOGE("new work failed");
322         delete dataWorker;
323         dataWorker = nullptr;
324         return;
325     }
326 
327     work->data = reinterpret_cast<void *>(dataWorker);
328 
329     int ret = uv_queue_work(loop, work, [](uv_work_t *work) {}, UvQueueWorkOnConsumed);
330     if (ret != 0) {
331         delete dataWorker;
332         dataWorker = nullptr;
333         delete work;
334         work = nullptr;
335     }
336 }
337 
UvQueueWorkOnUpdate(uv_work_t * work,int status)338 void UvQueueWorkOnUpdate(uv_work_t *work, int status)
339 {
340     ANS_LOGI("OnUpdate uv_work_t start");
341 
342     if (work == nullptr) {
343         ANS_LOGE("work is null");
344         return;
345     }
346     auto dataWorkerData = reinterpret_cast<NotificationReceiveDataWorker *>(work->data);
347     if (dataWorkerData == nullptr) {
348         ANS_LOGE("dataWorkerData is null");
349         delete work;
350         work = nullptr;
351         return;
352     }
353     napi_value result = nullptr;
354     napi_create_object(dataWorkerData->env, &result);
355     if (!Common::SetNotificationSortingMap(dataWorkerData->env, dataWorkerData->sortingMap, result)) {
356         ANS_LOGE("Failed to convert data to JS");
357     } else {
358         Common::SetCallback(dataWorkerData->env, dataWorkerData->ref, result);
359     }
360 
361     delete dataWorkerData;
362     dataWorkerData = nullptr;
363     delete work;
364 }
365 
OnUpdate(const std::shared_ptr<NotificationSortingMap> & sortingMap)366 void SubscriberInstance::OnUpdate(const std::shared_ptr<NotificationSortingMap> &sortingMap)
367 {
368     ANS_LOGI("enter");
369 
370     if (updateCallbackInfo_.ref == nullptr) {
371         ANS_LOGI("update callback unset");
372         return;
373     }
374 
375     if (sortingMap == nullptr) {
376         ANS_LOGE("sortingMap is null");
377         return;
378     }
379     ANS_LOGI("OnUpdate sortingMap size = %{public}zu", sortingMap->GetKey().size());
380 
381     uv_loop_s *loop = nullptr;
382     napi_get_uv_event_loop(updateCallbackInfo_.env, &loop);
383     if (loop == nullptr) {
384         ANS_LOGE("loop instance is nullptr");
385         return;
386     }
387 
388     NotificationReceiveDataWorker *dataWorker = new (std::nothrow) NotificationReceiveDataWorker();
389     if (dataWorker == nullptr) {
390         ANS_LOGE("new dataWorker failed");
391         return;
392     }
393 
394     dataWorker->sortingMap = sortingMap;
395     dataWorker->env = updateCallbackInfo_.env;
396     dataWorker->ref = updateCallbackInfo_.ref;
397 
398     uv_work_t *work = new (std::nothrow) uv_work_t;
399     if (work == nullptr) {
400         ANS_LOGE("new work failed");
401         delete dataWorker;
402         dataWorker = nullptr;
403         return;
404     }
405 
406     work->data = reinterpret_cast<void *>(dataWorker);
407 
408     int ret = uv_queue_work(loop, work, [](uv_work_t *work) {}, UvQueueWorkOnUpdate);
409     if (ret != 0) {
410         delete dataWorker;
411         dataWorker = nullptr;
412         delete work;
413         work = nullptr;
414     }
415 }
416 
UvQueueWorkOnConnected(uv_work_t * work,int status)417 void UvQueueWorkOnConnected(uv_work_t *work, int status)
418 {
419     ANS_LOGI("OnConnected uv_work_t start");
420 
421     if (work == nullptr) {
422         ANS_LOGE("work is null");
423         return;
424     }
425 
426     auto dataWorkerData = reinterpret_cast<NotificationReceiveDataWorker *>(work->data);
427     if (dataWorkerData == nullptr) {
428         ANS_LOGE("dataWorkerData is null");
429         delete work;
430         work = nullptr;
431         return;
432     }
433 
434     Common::SetCallback(dataWorkerData->env, dataWorkerData->ref, Common::NapiGetNull(dataWorkerData->env));
435 
436     delete dataWorkerData;
437     dataWorkerData = nullptr;
438     delete work;
439 }
440 
OnConnected()441 void SubscriberInstance::OnConnected()
442 {
443     ANS_LOGI("enter");
444 
445     if (subscribeCallbackInfo_.ref == nullptr) {
446         ANS_LOGI("subscribe callback unset");
447         return;
448     }
449 
450     uv_loop_s *loop = nullptr;
451     napi_get_uv_event_loop(subscribeCallbackInfo_.env, &loop);
452     if (loop == nullptr) {
453         ANS_LOGE("loop instance is nullptr");
454         return;
455     }
456 
457     NotificationReceiveDataWorker *dataWorker = new (std::nothrow) NotificationReceiveDataWorker();
458     if (dataWorker == nullptr) {
459         ANS_LOGE("new dataWorker failed");
460         return;
461     }
462 
463     dataWorker->env = subscribeCallbackInfo_.env;
464     dataWorker->ref = subscribeCallbackInfo_.ref;
465 
466     uv_work_t *work = new (std::nothrow) uv_work_t;
467     if (work == nullptr) {
468         ANS_LOGE("new work failed");
469         delete dataWorker;
470         dataWorker = nullptr;
471         return;
472     }
473 
474     work->data = reinterpret_cast<void *>(dataWorker);
475 
476     int ret = uv_queue_work(loop, work, [](uv_work_t *work) {}, UvQueueWorkOnConnected);
477     if (ret != 0) {
478         delete dataWorker;
479         dataWorker = nullptr;
480         delete work;
481         work = nullptr;
482     }
483 }
484 
UvQueueWorkOnDisconnected(uv_work_t * work,int status)485 void UvQueueWorkOnDisconnected(uv_work_t *work, int status)
486 {
487     ANS_LOGI("OnDisconnected uv_work_t start");
488 
489     if (work == nullptr) {
490         ANS_LOGE("work is null");
491         return;
492     }
493 
494     auto dataWorkerData = reinterpret_cast<NotificationReceiveDataWorker *>(work->data);
495     if (dataWorkerData == nullptr) {
496         ANS_LOGE("dataWorkerData is null");
497         delete work;
498         work = nullptr;
499         return;
500     }
501 
502     Common::SetCallback(dataWorkerData->env, dataWorkerData->ref, Common::NapiGetNull(dataWorkerData->env));
503 
504     DelSubscriberInstancesInfo(dataWorkerData->env, dataWorkerData->subscriber);
505 
506     delete dataWorkerData;
507     dataWorkerData = nullptr;
508     delete work;
509 }
510 
OnDisconnected()511 void SubscriberInstance::OnDisconnected()
512 {
513     ANS_LOGI("enter");
514 
515     if (unsubscribeCallbackInfo_.ref == nullptr) {
516         ANS_LOGI("unsubscribe callback unset");
517         return;
518     }
519 
520     uv_loop_s *loop = nullptr;
521     napi_get_uv_event_loop(unsubscribeCallbackInfo_.env, &loop);
522     if (loop == nullptr) {
523         ANS_LOGE("loop instance is nullptr");
524         return;
525     }
526 
527     NotificationReceiveDataWorker *dataWorker = new (std::nothrow) NotificationReceiveDataWorker();
528     if (dataWorker == nullptr) {
529         ANS_LOGE("new dataWorker failed");
530         return;
531     }
532 
533     dataWorker->env = unsubscribeCallbackInfo_.env;
534     dataWorker->ref = unsubscribeCallbackInfo_.ref;
535     dataWorker->subscriber = this;
536 
537     uv_work_t *work = new (std::nothrow) uv_work_t;
538     if (work == nullptr) {
539         ANS_LOGE("new work failed");
540         delete dataWorker;
541         dataWorker = nullptr;
542         return;
543     }
544 
545     work->data = reinterpret_cast<void *>(dataWorker);
546 
547     int ret = uv_queue_work(loop, work, [](uv_work_t *work) {}, UvQueueWorkOnDisconnected);
548     if (ret != 0) {
549         delete dataWorker;
550         dataWorker = nullptr;
551         delete work;
552         work = nullptr;
553     }
554 }
555 
UvQueueWorkOnDied(uv_work_t * work,int status)556 void UvQueueWorkOnDied(uv_work_t *work, int status)
557 {
558     ANS_LOGI("OnDied uv_work_t start");
559 
560     if (work == nullptr) {
561         ANS_LOGE("work is null");
562         return;
563     }
564     auto dataWorkerData = reinterpret_cast<NotificationReceiveDataWorker *>(work->data);
565     if (dataWorkerData == nullptr) {
566         ANS_LOGE("dataWorkerData is null");
567         delete work;
568         work = nullptr;
569         return;
570     }
571 
572     Common::SetCallback(
573         dataWorkerData->env, dataWorkerData->ref, Common::NapiGetNull(dataWorkerData->env));
574 
575     delete dataWorkerData;
576     dataWorkerData = nullptr;
577     delete work;
578 }
579 
OnDied()580 void SubscriberInstance::OnDied()
581 {
582     ANS_LOGI("enter");
583 
584     if (dieCallbackInfo_.ref == nullptr) {
585         ANS_LOGE("die callback unset");
586         return;
587     }
588 
589     uv_loop_s *loop = nullptr;
590     napi_get_uv_event_loop(dieCallbackInfo_.env, &loop);
591     if (loop == nullptr) {
592         ANS_LOGE("loop instance is nullptr");
593         return;
594     }
595 
596     NotificationReceiveDataWorker *dataWorker = new (std::nothrow) NotificationReceiveDataWorker();
597     if (dataWorker == nullptr) {
598         ANS_LOGE("new dataWorker failed");
599         return;
600     }
601 
602     dataWorker->env = dieCallbackInfo_.env;
603     dataWorker->ref = dieCallbackInfo_.ref;
604 
605     uv_work_t *work = new (std::nothrow) uv_work_t;
606     if (work == nullptr) {
607         ANS_LOGE("new work failed");
608         delete dataWorker;
609         dataWorker = nullptr;
610         return;
611     }
612 
613     work->data = reinterpret_cast<void *>(dataWorker);
614 
615     int ret = uv_queue_work(loop, work, [](uv_work_t *work) {}, UvQueueWorkOnDied);
616     if (ret != 0) {
617         delete dataWorker;
618         dataWorker = nullptr;
619         delete work;
620         work = nullptr;
621     }
622 }
623 
UvQueueWorkOnDoNotDisturbDateChange(uv_work_t * work,int status)624 void UvQueueWorkOnDoNotDisturbDateChange(uv_work_t *work, int status)
625 {
626     ANS_LOGI("OnDoNotDisturbDateChange uv_work_t start");
627 
628     if (work == nullptr) {
629         ANS_LOGE("work is null");
630         return;
631     }
632 
633     auto dataWorkerData = reinterpret_cast<NotificationReceiveDataWorker *>(work->data);
634     if (dataWorkerData == nullptr) {
635         ANS_LOGE("dataWorkerData is null");
636         delete work;
637         work = nullptr;
638         return;
639     }
640 
641     napi_value result = nullptr;
642     napi_create_object(dataWorkerData->env, &result);
643 
644     if (!Common::SetDoNotDisturbDate(dataWorkerData->env, dataWorkerData->date, result)) {
645         result = Common::NapiGetNull(dataWorkerData->env);
646     }
647 
648     Common::SetCallback(dataWorkerData->env, dataWorkerData->ref, result);
649 
650     delete dataWorkerData;
651     dataWorkerData = nullptr;
652     delete work;
653 }
654 
OnDoNotDisturbDateChange(const std::shared_ptr<NotificationDoNotDisturbDate> & date)655 void SubscriberInstance::OnDoNotDisturbDateChange(const std::shared_ptr<NotificationDoNotDisturbDate> &date)
656 {
657     ANS_LOGI("enter");
658 
659     if (disturbDateCallbackInfo_.ref == nullptr) {
660         ANS_LOGI("disturbDateCallbackInfo_ callback unset");
661         return;
662     }
663 
664     if (date == nullptr) {
665         ANS_LOGE("date is null");
666         return;
667     }
668 
669     uv_loop_s *loop = nullptr;
670     napi_get_uv_event_loop(disturbDateCallbackInfo_.env, &loop);
671     if (loop == nullptr) {
672         ANS_LOGE("loop instance is nullptr");
673         return;
674     }
675 
676     NotificationReceiveDataWorker *dataWorker = new (std::nothrow) NotificationReceiveDataWorker();
677     if (dataWorker == nullptr) {
678         ANS_LOGE("new dataWorker failed");
679         return;
680     }
681 
682     dataWorker->date = *date;
683     dataWorker->env = disturbDateCallbackInfo_.env;
684     dataWorker->ref = disturbDateCallbackInfo_.ref;
685 
686     uv_work_t *work = new (std::nothrow) uv_work_t;
687     if (work == nullptr) {
688         ANS_LOGE("new work failed");
689         delete dataWorker;
690         dataWorker = nullptr;
691         return;
692     }
693 
694     work->data = reinterpret_cast<void *>(dataWorker);
695 
696     int ret = uv_queue_work(loop, work, [](uv_work_t *work) {}, UvQueueWorkOnDoNotDisturbDateChange);
697     if (ret != 0) {
698         delete dataWorker;
699         dataWorker = nullptr;
700         delete work;
701         work = nullptr;
702     }
703 }
704 
UvQueueWorkOnEnabledNotificationChanged(uv_work_t * work,int status)705 void UvQueueWorkOnEnabledNotificationChanged(uv_work_t *work, int status)
706 {
707     ANS_LOGI("OnEnabledNotificationChanged uv_work_t start");
708 
709     if (work == nullptr) {
710         ANS_LOGE("work is null");
711         return;
712     }
713 
714     auto dataWorkerData = reinterpret_cast<NotificationReceiveDataWorker *>(work->data);
715     if (dataWorkerData == nullptr) {
716         ANS_LOGE("dataWorkerData is null");
717         delete work;
718         work = nullptr;
719         return;
720     }
721 
722     napi_value result = nullptr;
723     napi_create_object(dataWorkerData->env, &result);
724 
725     if (!Common::SetEnabledNotificationCallbackData(dataWorkerData->env, dataWorkerData->callbackData, result)) {
726         result = Common::NapiGetNull(dataWorkerData->env);
727     }
728 
729     Common::SetCallback(dataWorkerData->env, dataWorkerData->ref, result);
730 
731     delete dataWorkerData;
732     dataWorkerData = nullptr;
733     delete work;
734 }
735 
OnEnabledNotificationChanged(const std::shared_ptr<EnabledNotificationCallbackData> & callbackData)736 void SubscriberInstance::OnEnabledNotificationChanged(
737     const std::shared_ptr<EnabledNotificationCallbackData> &callbackData)
738 {
739     ANS_LOGI("enter");
740 
741     if (enabledNotificationCallbackInfo_.ref == nullptr) {
742         ANS_LOGI("enabledNotificationCallbackInfo_ callback unset");
743         return;
744     }
745 
746     if (callbackData == nullptr) {
747         ANS_LOGE("callbackData is null");
748         return;
749     }
750 
751     uv_loop_s *loop = nullptr;
752     napi_get_uv_event_loop(enabledNotificationCallbackInfo_.env, &loop);
753     if (loop == nullptr) {
754         ANS_LOGE("loop instance is nullptr");
755         return;
756     }
757 
758     NotificationReceiveDataWorker *dataWorker = new (std::nothrow) NotificationReceiveDataWorker();
759     if (dataWorker == nullptr) {
760         ANS_LOGE("new dataWorker failed");
761         return;
762     }
763 
764     dataWorker->callbackData = *callbackData;
765     dataWorker->env = enabledNotificationCallbackInfo_.env;
766     dataWorker->ref = enabledNotificationCallbackInfo_.ref;
767 
768     uv_work_t *work = new (std::nothrow) uv_work_t;
769     if (work == nullptr) {
770         ANS_LOGE("new work failed");
771         delete dataWorker;
772         dataWorker = nullptr;
773         return;
774     }
775 
776     work->data = reinterpret_cast<void *>(dataWorker);
777 
778     int ret = uv_queue_work(loop, work, [](uv_work_t *work) {}, UvQueueWorkOnEnabledNotificationChanged);
779     if (ret != 0) {
780         delete dataWorker;
781         dataWorker = nullptr;
782         delete work;
783         work = nullptr;
784     }
785 }
786 
SetCancelCallbackInfo(const napi_env & env,const napi_ref & ref)787 void SubscriberInstance::SetCancelCallbackInfo(const napi_env &env, const napi_ref &ref)
788 {
789     canceCallbackInfo_.env = env;
790     canceCallbackInfo_.ref = ref;
791 }
792 
SetConsumeCallbackInfo(const napi_env & env,const napi_ref & ref)793 void SubscriberInstance::SetConsumeCallbackInfo(const napi_env &env, const napi_ref &ref)
794 {
795     consumeCallbackInfo_.env = env;
796     consumeCallbackInfo_.ref = ref;
797 }
798 
SetUpdateCallbackInfo(const napi_env & env,const napi_ref & ref)799 void SubscriberInstance::SetUpdateCallbackInfo(const napi_env &env, const napi_ref &ref)
800 {
801     updateCallbackInfo_.env = env;
802     updateCallbackInfo_.ref = ref;
803 }
804 
SetSubscribeCallbackInfo(const napi_env & env,const napi_ref & ref)805 void SubscriberInstance::SetSubscribeCallbackInfo(const napi_env &env, const napi_ref &ref)
806 {
807     subscribeCallbackInfo_.env = env;
808     subscribeCallbackInfo_.ref = ref;
809 }
810 
SetUnsubscribeCallbackInfo(const napi_env & env,const napi_ref & ref)811 void SubscriberInstance::SetUnsubscribeCallbackInfo(const napi_env &env, const napi_ref &ref)
812 {
813     unsubscribeCallbackInfo_.env = env;
814     unsubscribeCallbackInfo_.ref = ref;
815 }
816 
SetDieCallbackInfo(const napi_env & env,const napi_ref & ref)817 void SubscriberInstance::SetDieCallbackInfo(const napi_env &env, const napi_ref &ref)
818 {
819     dieCallbackInfo_.env = env;
820     dieCallbackInfo_.ref = ref;
821 }
822 
SetDisturbModeCallbackInfo(const napi_env & env,const napi_ref & ref)823 void SubscriberInstance::SetDisturbModeCallbackInfo(const napi_env &env, const napi_ref &ref)
824 {
825     disturbModeCallbackInfo_.env = env;
826     disturbModeCallbackInfo_.ref = ref;
827 }
828 
SetEnabledNotificationCallbackInfo(const napi_env & env,const napi_ref & ref)829 void SubscriberInstance::SetEnabledNotificationCallbackInfo(const napi_env &env, const napi_ref &ref)
830 {
831     enabledNotificationCallbackInfo_.env = env;
832     enabledNotificationCallbackInfo_.ref = ref;
833 }
834 
SetDisturbDateCallbackInfo(const napi_env & env,const napi_ref & ref)835 void SubscriberInstance::SetDisturbDateCallbackInfo(const napi_env &env, const napi_ref &ref)
836 {
837     disturbDateCallbackInfo_.env = env;
838     disturbDateCallbackInfo_.ref = ref;
839 }
840 
SetCallbackInfo(const napi_env & env,const std::string & type,const napi_ref & ref)841 void SubscriberInstance::SetCallbackInfo(const napi_env &env, const std::string &type, const napi_ref &ref)
842 {
843     if (type == CONSUME) {
844         SetConsumeCallbackInfo(env, ref);
845     } else if (type == CANCEL) {
846         SetCancelCallbackInfo(env, ref);
847     } else if (type == UPDATE) {
848         SetUpdateCallbackInfo(env, ref);
849     } else if (type == CONNECTED) {
850         SetSubscribeCallbackInfo(env, ref);
851     } else if (type == DIS_CONNECTED) {
852         SetUnsubscribeCallbackInfo(env, ref);
853     } else if (type == DIE) {
854         SetDieCallbackInfo(env, ref);
855     } else if (type == DISTURB_MODE_CHANGE) {
856         SetDisturbModeCallbackInfo(env, ref);
857     } else if (type == DISTURB_DATE_CHANGE) {
858         SetDisturbDateCallbackInfo(env, ref);
859     } else if (type == ENABLE_NOTIFICATION_CHANGED) {
860         SetEnabledNotificationCallbackInfo(env, ref);
861     } else {
862         ANS_LOGW("type is error");
863     }
864 }
865 
HasNotificationSubscriber(const napi_env & env,const napi_value & value,SubscriberInstancesInfo & subscriberInfo)866 bool HasNotificationSubscriber(const napi_env &env, const napi_value &value, SubscriberInstancesInfo &subscriberInfo)
867 {
868     std::lock_guard<std::mutex> lock(mutex_);
869     for (auto vec : subscriberInstances_) {
870         napi_value callback = nullptr;
871         napi_get_reference_value(env, vec.ref, &callback);
872         bool isEquals = false;
873         napi_strict_equals(env, value, callback, &isEquals);
874         if (isEquals) {
875             subscriberInfo = vec;
876             return true;
877         }
878     }
879     return false;
880 }
881 
GetNotificationSubscriber(const napi_env & env,const napi_value & value,SubscriberInstancesInfo & subscriberInfo)882 napi_value GetNotificationSubscriber(
883     const napi_env &env, const napi_value &value, SubscriberInstancesInfo &subscriberInfo)
884 {
885     ANS_LOGI("enter");
886     bool hasProperty = false;
887     napi_valuetype valuetype = napi_undefined;
888     napi_ref result = nullptr;
889 
890     subscriberInfo.subscriber = new (std::nothrow) SubscriberInstance();
891     if (subscriberInfo.subscriber == nullptr) {
892         ANS_LOGE("subscriber is null");
893         return nullptr;
894     }
895 
896     napi_create_reference(env, value, 1, &subscriberInfo.ref);
897 
898     // onConsume?:(data: SubscribeCallbackData) => void
899     NAPI_CALL(env, napi_has_named_property(env, value, "onConsume", &hasProperty));
900     if (hasProperty) {
901         napi_value nOnConsumed = nullptr;
902         napi_get_named_property(env, value, "onConsume", &nOnConsumed);
903         NAPI_CALL(env, napi_typeof(env, nOnConsumed, &valuetype));
904         if (valuetype != napi_function) {
905             ANS_LOGE("Wrong argument type. Function expected.");
906             return nullptr;
907         }
908         napi_create_reference(env, nOnConsumed, 1, &result);
909         subscriberInfo.subscriber->SetCallbackInfo(env, CONSUME, result);
910     }
911     // onCancel?:(data: SubscribeCallbackData) => void
912     NAPI_CALL(env, napi_has_named_property(env, value, "onCancel", &hasProperty));
913     if (hasProperty) {
914         napi_value nOnCanceled = nullptr;
915         napi_get_named_property(env, value, "onCancel", &nOnCanceled);
916         NAPI_CALL(env, napi_typeof(env, nOnCanceled, &valuetype));
917         if (valuetype != napi_function) {
918             ANS_LOGE("Wrong argument type. Function expected.");
919             return nullptr;
920         }
921         napi_create_reference(env, nOnCanceled, 1, &result);
922         subscriberInfo.subscriber->SetCallbackInfo(env, CANCEL, result);
923     }
924     // onUpdate?:(data: NotificationSortingMap) => void
925     NAPI_CALL(env, napi_has_named_property(env, value, "onUpdate", &hasProperty));
926     if (hasProperty) {
927         napi_value nOnUpdate = nullptr;
928         napi_get_named_property(env, value, "onUpdate", &nOnUpdate);
929         NAPI_CALL(env, napi_typeof(env, nOnUpdate, &valuetype));
930         if (valuetype != napi_function) {
931             ANS_LOGE("Wrong argument type. Function expected.");
932             return nullptr;
933         }
934         napi_create_reference(env, nOnUpdate, 1, &result);
935         subscriberInfo.subscriber->SetCallbackInfo(env, UPDATE, result);
936     }
937     // onConnect?:() => void
938     NAPI_CALL(env, napi_has_named_property(env, value, "onConnect", &hasProperty));
939     if (hasProperty) {
940         napi_value nOnConnected = nullptr;
941         napi_get_named_property(env, value, "onConnect", &nOnConnected);
942         NAPI_CALL(env, napi_typeof(env, nOnConnected, &valuetype));
943         if (valuetype != napi_function) {
944             ANS_LOGE("Wrong argument type. Function expected.");
945             return nullptr;
946         }
947         napi_create_reference(env, nOnConnected, 1, &result);
948         subscriberInfo.subscriber->SetCallbackInfo(env, CONNECTED, result);
949     }
950     // onDisconnect?:() => void
951     NAPI_CALL(env, napi_has_named_property(env, value, "onDisconnect", &hasProperty));
952     if (hasProperty) {
953         napi_value nOnDisConnect = nullptr;
954         napi_get_named_property(env, value, "onDisconnect", &nOnDisConnect);
955         NAPI_CALL(env, napi_typeof(env, nOnDisConnect, &valuetype));
956         if (valuetype != napi_function) {
957             ANS_LOGE("Wrong argument type. Function expected.");
958             return nullptr;
959         }
960         napi_create_reference(env, nOnDisConnect, 1, &result);
961         subscriberInfo.subscriber->SetCallbackInfo(env, DIS_CONNECTED, result);
962     }
963     // onDestroy?:() => void
964     NAPI_CALL(env, napi_has_named_property(env, value, "onDestroy", &hasProperty));
965     if (hasProperty) {
966         napi_value nOnDied = nullptr;
967         napi_get_named_property(env, value, "onDestroy", &nOnDied);
968         NAPI_CALL(env, napi_typeof(env, nOnDied, &valuetype));
969         if (valuetype != napi_function) {
970             ANS_LOGE("Wrong argument type. Function expected.");
971             return nullptr;
972         }
973         napi_create_reference(env, nOnDied, 1, &result);
974         subscriberInfo.subscriber->SetCallbackInfo(env, DIE, result);
975     }
976     // onDisturbModeChange?:(mode: notification.DoNotDisturbMode) => void
977     NAPI_CALL(env, napi_has_named_property(env, value, "onDisturbModeChange", &hasProperty));
978     if (hasProperty) {
979         napi_value nOnDisturbModeChanged = nullptr;
980         napi_get_named_property(env, value, "onDisturbModeChange", &nOnDisturbModeChanged);
981         NAPI_CALL(env, napi_typeof(env, nOnDisturbModeChanged, &valuetype));
982         if (valuetype != napi_function) {
983             ANS_LOGE("Wrong argument type. Function expected.");
984             return nullptr;
985         }
986         napi_create_reference(env, nOnDisturbModeChanged, 1, &result);
987         subscriberInfo.subscriber->SetCallbackInfo(env, DISTURB_MODE_CHANGE, result);
988     }
989 
990     // onDoNotDisturbDateChange?:(mode: notification.DoNotDisturbDate) => void
991     NAPI_CALL(env, napi_has_named_property(env, value, "onDoNotDisturbDateChange", &hasProperty));
992     if (hasProperty) {
993         napi_value nOnDisturbDateChanged = nullptr;
994         napi_get_named_property(env, value, "onDoNotDisturbDateChange", &nOnDisturbDateChanged);
995         NAPI_CALL(env, napi_typeof(env, nOnDisturbDateChanged, &valuetype));
996         if (valuetype != napi_function) {
997             ANS_LOGE("Wrong argument type. Function expected.");
998             return nullptr;
999         }
1000         napi_create_reference(env, nOnDisturbDateChanged, 1, &result);
1001         subscriberInfo.subscriber->SetCallbackInfo(env, DISTURB_DATE_CHANGE, result);
1002     }
1003 
1004     // onEnabledNotificationChanged?:(data: notification.EnabledNotificationCallbackData) => void
1005     NAPI_CALL(env, napi_has_named_property(env, value, "onEnabledNotificationChanged", &hasProperty));
1006     if (hasProperty) {
1007         napi_value nOnEnabledNotificationChanged = nullptr;
1008         napi_get_named_property(env, value, "onEnabledNotificationChanged", &nOnEnabledNotificationChanged);
1009         NAPI_CALL(env, napi_typeof(env, nOnEnabledNotificationChanged, &valuetype));
1010         if (valuetype != napi_function) {
1011             ANS_LOGE("Wrong argument type. Function expected.");
1012             return nullptr;
1013         }
1014         napi_create_reference(env, nOnEnabledNotificationChanged, 1, &result);
1015         subscriberInfo.subscriber->SetCallbackInfo(env, ENABLE_NOTIFICATION_CHANGED, result);
1016     }
1017 
1018     return Common::NapiGetNull(env);
1019 }
1020 
AddSubscriberInstancesInfo(const napi_env & env,const SubscriberInstancesInfo & subscriberInfo)1021 bool AddSubscriberInstancesInfo(const napi_env &env, const SubscriberInstancesInfo &subscriberInfo)
1022 {
1023     ANS_LOGI("enter");
1024     if (subscriberInfo.ref == nullptr) {
1025         ANS_LOGE("subscriberInfo.ref is null");
1026         return false;
1027     }
1028     if (subscriberInfo.subscriber == nullptr) {
1029         ANS_LOGE("subscriberInfo.subscriber is null");
1030         return false;
1031     }
1032     std::lock_guard<std::mutex> lock(mutex_);
1033     subscriberInstances_.emplace_back(subscriberInfo);
1034 
1035     return true;
1036 }
1037 
DelSubscriberInstancesInfo(const napi_env & env,const SubscriberInstance * subscriber)1038 bool DelSubscriberInstancesInfo(const napi_env &env, const SubscriberInstance *subscriber)
1039 {
1040     ANS_LOGI("enter");
1041     if (subscriber == nullptr) {
1042         ANS_LOGE("subscriber is null");
1043         return false;
1044     }
1045 
1046     std::lock_guard<std::mutex> lock(mutex_);
1047     for (auto it = subscriberInstances_.begin(); it != subscriberInstances_.end(); ++it) {
1048         if ((*it).subscriber == subscriber) {
1049             if ((*it).ref != nullptr) {
1050                 napi_delete_reference(env, (*it).ref);
1051             }
1052             DelDeletingSubscriber((*it).subscriber);
1053             delete (*it).subscriber;
1054             (*it).subscriber = nullptr;
1055             subscriberInstances_.erase(it);
1056             return true;
1057         }
1058     }
1059     return false;
1060 }
ParseParameters(const napi_env & env,const napi_callback_info & info,NotificationSubscribeInfo & subscriberInfo,SubscriberInstance * & subscriber,napi_ref & callback)1061 napi_value ParseParameters(const napi_env &env, const napi_callback_info &info,
1062     NotificationSubscribeInfo &subscriberInfo, SubscriberInstance *&subscriber, napi_ref &callback)
1063 {
1064     ANS_LOGI("enter");
1065 
1066     size_t argc = SUBSRIBE_MAX_PARA;
1067     napi_value argv[SUBSRIBE_MAX_PARA] = {nullptr};
1068     napi_value thisVar = nullptr;
1069     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, NULL));
1070     if (argc < 1) {
1071         ANS_LOGE("Wrong number of arguments");
1072         return nullptr;
1073     }
1074 
1075     napi_valuetype valuetype = napi_undefined;
1076 
1077     // argv[0]:subscriber
1078     NAPI_CALL(env, napi_typeof(env, argv[PARAM0], &valuetype));
1079     if (valuetype != napi_object) {
1080         ANS_LOGE("Wrong argument type for arg0. NotificationSubscriber object expected.");
1081         return nullptr;
1082     }
1083 
1084     SubscriberInstancesInfo subscriberInstancesInfo;
1085     if (!HasNotificationSubscriber(env, argv[PARAM0], subscriberInstancesInfo)) {
1086         if (GetNotificationSubscriber(env, argv[PARAM0], subscriberInstancesInfo) == nullptr) {
1087             ANS_LOGE("NotificationSubscriber parse failed");
1088             if (subscriberInstancesInfo.subscriber) {
1089                 delete subscriberInstancesInfo.subscriber;
1090                 subscriberInstancesInfo.subscriber = nullptr;
1091             }
1092             return nullptr;
1093         }
1094         if (!AddSubscriberInstancesInfo(env, subscriberInstancesInfo)) {
1095             ANS_LOGE("AddSubscriberInstancesInfo add failed");
1096             if (subscriberInstancesInfo.subscriber) {
1097                 delete subscriberInstancesInfo.subscriber;
1098                 subscriberInstancesInfo.subscriber = nullptr;
1099             }
1100             return nullptr;
1101         }
1102     }
1103     subscriber = subscriberInstancesInfo.subscriber;
1104 
1105     // argv[1]:callback or NotificationSubscribeInfo
1106     if (argc >= SUBSRIBE_MAX_PARA - 1) {
1107         NAPI_CALL(env, napi_typeof(env, argv[PARAM1], &valuetype));
1108         if ((valuetype != napi_function) && (valuetype != napi_object)) {
1109             ANS_LOGE("Wrong argument type for arg1. Function or NotificationSubscribeInfo object expected.");
1110             return nullptr;
1111         }
1112         if (valuetype == napi_function) {
1113             napi_create_reference(env, argv[PARAM1], 1, &callback);
1114         } else {
1115             if (Common::GetNotificationSubscriberInfo(env, argv[PARAM1], subscriberInfo) == nullptr) {
1116                 ANS_LOGE("NotificationSubscribeInfo parse failed");
1117                 return nullptr;
1118             }
1119         }
1120     }
1121 
1122     // argv[2]:callback
1123     if (argc >= SUBSRIBE_MAX_PARA) {
1124         NAPI_CALL(env, napi_typeof(env, argv[PARAM2], &valuetype));
1125         if (valuetype != napi_function) {
1126             ANS_LOGE("Wrong argument type. Function expected.");
1127             return nullptr;
1128         }
1129         napi_create_reference(env, argv[PARAM2], 1, &callback);
1130     }
1131 
1132     return Common::NapiGetNull(env);
1133 }
1134 
Subscribe(napi_env env,napi_callback_info info)1135 napi_value Subscribe(napi_env env, napi_callback_info info)
1136 {
1137     ANS_LOGI("enter");
1138 
1139     napi_ref callback = nullptr;
1140     SubscriberInstance *objectInfo = nullptr;
1141     NotificationSubscribeInfo subscriberInfo;
1142     if (ParseParameters(env, info, subscriberInfo, objectInfo, callback) == nullptr) {
1143         if (objectInfo) {
1144             delete objectInfo;
1145             objectInfo = nullptr;
1146         }
1147         return Common::NapiGetUndefined(env);
1148     }
1149 
1150     AsyncCallbackInfoSubscribe *asynccallbackinfo = new (std::nothrow) AsyncCallbackInfoSubscribe {
1151         .env = env, .asyncWork = nullptr, .objectInfo = objectInfo, .subscriberInfo = subscriberInfo
1152     };
1153     if (!asynccallbackinfo) {
1154         if (objectInfo) {
1155             delete objectInfo;
1156             objectInfo = nullptr;
1157         }
1158         return Common::JSParaError(env, callback);
1159     }
1160     napi_value promise = nullptr;
1161     Common::PaddingCallbackPromiseInfo(env, callback, asynccallbackinfo->info, promise);
1162 
1163     napi_value resourceName = nullptr;
1164     napi_create_string_latin1(env, "subscribeNotification", NAPI_AUTO_LENGTH, &resourceName);
1165     // Asynchronous function call
1166     napi_create_async_work(env,
1167         nullptr,
1168         resourceName,
1169         [](napi_env env, void *data) {
1170             ANS_LOGI("Subscribe napi_create_async_work start");
1171             if (!data) {
1172                 ANS_LOGE("Invalid asynccallbackinfo!");
1173                 return;
1174             }
1175             auto asynccallbackinfo = reinterpret_cast<AsyncCallbackInfoSubscribe *>(data);
1176             if (asynccallbackinfo) {
1177                 if (asynccallbackinfo->subscriberInfo.hasSubscribeInfo) {
1178                     ANS_LOGI("Subscribe with NotificationSubscribeInfo");
1179                     OHOS::Notification::NotificationSubscribeInfo subscribeInfo;
1180                     subscribeInfo.AddAppNames(asynccallbackinfo->subscriberInfo.bundleNames);
1181                     subscribeInfo.AddAppUserId(asynccallbackinfo->subscriberInfo.userId);
1182                     asynccallbackinfo->info.errorCode =
1183                         NotificationHelper::SubscribeNotification(*(asynccallbackinfo->objectInfo), subscribeInfo);
1184                 } else {
1185                     asynccallbackinfo->info.errorCode =
1186                         NotificationHelper::SubscribeNotification(*(asynccallbackinfo->objectInfo));
1187                 }
1188             }
1189         },
1190         [](napi_env env, napi_status status, void *data) {
1191             ANS_LOGI("Subscribe napi_create_async_work end");
1192             if (!data) {
1193                 ANS_LOGE("Invalid asynccallbackinfo!");
1194                 return;
1195             }
1196             auto asynccallbackinfo = reinterpret_cast<AsyncCallbackInfoSubscribe *>(data);
1197             if (asynccallbackinfo) {
1198                 Common::ReturnCallbackPromise(env, asynccallbackinfo->info, Common::NapiGetNull(env));
1199 
1200                 if (asynccallbackinfo->info.callback != nullptr) {
1201                     napi_delete_reference(env, asynccallbackinfo->info.callback);
1202                 }
1203                 napi_delete_async_work(env, asynccallbackinfo->asyncWork);
1204 
1205                 delete asynccallbackinfo;
1206                 asynccallbackinfo = nullptr;
1207             }
1208         },
1209         (void *)asynccallbackinfo,
1210         &asynccallbackinfo->asyncWork);
1211 
1212     NAPI_CALL(env, napi_queue_async_work(env, asynccallbackinfo->asyncWork));
1213 
1214     if (asynccallbackinfo->info.isCallback) {
1215         return Common::NapiGetNull(env);
1216     } else {
1217         return promise;
1218     }
1219 }
1220 
AddDeletingSubscriber(SubscriberInstance * subscriber)1221 bool AddDeletingSubscriber(SubscriberInstance *subscriber)
1222 {
1223     std::lock_guard<std::mutex> lock(delMutex_);
1224     auto iter = std::find(DeletingSubscriber.begin(), DeletingSubscriber.end(), subscriber);
1225     if (iter != DeletingSubscriber.end()) {
1226         return false;
1227     }
1228 
1229     DeletingSubscriber.push_back(subscriber);
1230     return true;
1231 }
1232 
DelDeletingSubscriber(SubscriberInstance * subscriber)1233 void DelDeletingSubscriber(SubscriberInstance *subscriber)
1234 {
1235     std::lock_guard<std::mutex> lock(delMutex_);
1236     auto iter = std::find(DeletingSubscriber.begin(), DeletingSubscriber.end(), subscriber);
1237     if (iter != DeletingSubscriber.end()) {
1238         DeletingSubscriber.erase(iter);
1239     }
1240 }
1241 }  // namespace NotificationNapi
1242 }  // namespace OHOS