1 /*
2 * Copyright (C) 2022 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 #include "location_napi_event.h"
16
17 #include "callback_manager.h"
18 #include "common_utils.h"
19 #include "location_log.h"
20 #include "location_napi_errcode.h"
21 #include "country_code_callback_napi.h"
22 #include "locator.h"
23 #include "geofence_sdk.h"
24 #include "geofence_napi.h"
25 #include "napi_util.h"
26 #ifdef SUPPORT_JSSTACK
27 #include "xpower_event_js.h"
28 #endif
29 #include "want_agent_helper.h"
30
31 namespace OHOS {
32 namespace Location {
33 CallbackManager<LocationSwitchCallbackNapi> g_switchCallbacks;
34 CallbackManager<LocatorCallbackNapi> g_locationCallbacks;
35 CallbackManager<GnssStatusCallbackNapi> g_gnssStatusInfoCallbacks;
36 CallbackManager<NmeaMessageCallbackNapi> g_nmeaCallbacks;
37 CallbackManager<CachedLocationsCallbackNapi> g_cachedLocationCallbacks;
38 CallbackManager<CountryCodeCallbackNapi> g_countryCodeCallbacks;
39 CallbackManager<LocatingRequiredDataCallbackNapi> g_locatingRequiredDataCallbacks;
40 CallbackManager<LocationErrorCallbackNapi> g_locationErrorCallbackHosts;
41
42 std::unique_ptr<CachedGnssLocationsRequest> g_cachedRequest = std::make_unique<CachedGnssLocationsRequest>();
43 auto g_locatorProxy = Locator::GetInstance();
44 auto g_geofenceProxy = GeofenceManager::GetInstance();
45
46 std::mutex g_FuncMapMutex;
47 std::map<std::string, bool(*)(const napi_env &)> g_offAllFuncMap;
48 std::map<std::string, bool(*)(const napi_env &, const napi_value &)> g_offFuncMap;
49 std::map<std::string, bool(*)(const napi_env &, const size_t, const napi_value *)> g_onFuncMap;
50
51
52 const int MIN_TIMEOUTMS_FOR_LOCATIONONCE = 1000;
53
InitOnFuncMap()54 void InitOnFuncMap()
55 {
56 std::unique_lock<std::mutex> lock(g_FuncMapMutex);
57 if (g_onFuncMap.size() != 0) {
58 return;
59 }
60 #ifdef ENABLE_NAPI_MANAGER
61 g_onFuncMap.insert(std::make_pair("locationEnabledChange", &OnLocationServiceStateCallback));
62 g_onFuncMap.insert(std::make_pair("cachedGnssLocationsChange", &OnCachedGnssLocationsReportingCallback));
63 g_onFuncMap.insert(std::make_pair("satelliteStatusChange", &OnGnssStatusChangeCallback));
64 g_onFuncMap.insert(std::make_pair("gnssFenceStatusChange", &OnFenceStatusChangeCallback));
65 g_onFuncMap.insert(std::make_pair("nmeaMessage", &OnNmeaMessageChangeCallback));
66 g_onFuncMap.insert(std::make_pair("locatingRequiredDataChange", &OnLocatingRequiredDataChangeCallback));
67 g_onFuncMap.insert(std::make_pair("locationError", &OnLocationErrorCallback));
68 #else
69 g_onFuncMap.insert(std::make_pair("locationServiceState", &OnLocationServiceStateCallback));
70 g_onFuncMap.insert(std::make_pair("cachedGnssLocationsReporting", &OnCachedGnssLocationsReportingCallback));
71 g_onFuncMap.insert(std::make_pair("gnssStatusChange", &OnGnssStatusChangeCallback));
72 g_onFuncMap.insert(std::make_pair("fenceStatusChange", &OnFenceStatusChangeCallback));
73 g_onFuncMap.insert(std::make_pair("nmeaMessageChange", &OnNmeaMessageChangeCallback));
74 #endif
75 g_onFuncMap.insert(std::make_pair("locationChange", &OnLocationChangeCallback));
76 g_onFuncMap.insert(std::make_pair("countryCodeChange", &OnCountryCodeChangeCallback));
77 }
78
InitOffFuncMap()79 void InitOffFuncMap()
80 {
81 std::unique_lock<std::mutex> lock(g_FuncMapMutex);
82 if (g_offAllFuncMap.size() != 0 || g_offFuncMap.size() != 0) {
83 return;
84 }
85 #ifdef ENABLE_NAPI_MANAGER
86 g_offAllFuncMap.insert(std::make_pair("locationEnabledChange", &OffAllLocationServiceStateCallback));
87 g_offAllFuncMap.insert(std::make_pair("cachedGnssLocationsChange", &OffAllCachedGnssLocationsReportingCallback));
88 g_offAllFuncMap.insert(std::make_pair("satelliteStatusChange", &OffAllGnssStatusChangeCallback));
89 g_offAllFuncMap.insert(std::make_pair("nmeaMessage", &OffAllNmeaMessageChangeCallback));
90 g_offAllFuncMap.insert(std::make_pair("locatingRequiredDataChange", &OffAllLocatingRequiredDataChangeCallback));
91 #else
92 g_offAllFuncMap.insert(std::make_pair("locationServiceState", &OffAllLocationServiceStateCallback));
93 g_offAllFuncMap.insert(std::make_pair("cachedGnssLocationsReporting", &OffAllCachedGnssLocationsReportingCallback));
94 g_offAllFuncMap.insert(std::make_pair("gnssStatusChange", &OffAllGnssStatusChangeCallback));
95 g_offAllFuncMap.insert(std::make_pair("nmeaMessageChange", &OffAllNmeaMessageChangeCallback));
96 #endif
97 g_offAllFuncMap.insert(std::make_pair("locationChange", &OffAllLocationChangeCallback));
98 g_offAllFuncMap.insert(std::make_pair("countryCodeChange", &OffAllCountryCodeChangeCallback));
99
100 #ifdef ENABLE_NAPI_MANAGER
101 g_offFuncMap.insert(std::make_pair("locationEnabledChange", &OffLocationServiceStateCallback));
102 g_offFuncMap.insert(std::make_pair("cachedGnssLocationsChange", &OffCachedGnssLocationsReportingCallback));
103 g_offFuncMap.insert(std::make_pair("satelliteStatusChange", &OffGnssStatusChangeCallback));
104 g_offFuncMap.insert(std::make_pair("nmeaMessage", &OffNmeaMessageChangeCallback));
105 g_offFuncMap.insert(std::make_pair("locatingRequiredDataChange", &OffLocatingRequiredDataChangeCallback));
106 g_offFuncMap.insert(std::make_pair("locationError", &OffLocationErrorCallback));
107 #else
108 g_offFuncMap.insert(std::make_pair("locationServiceState", &OffLocationServiceStateCallback));
109 g_offFuncMap.insert(std::make_pair("cachedGnssLocationsReporting", &OffCachedGnssLocationsReportingCallback));
110 g_offFuncMap.insert(std::make_pair("gnssStatusChange", &OffGnssStatusChangeCallback));
111 g_offFuncMap.insert(std::make_pair("nmeaMessageChange", &OffNmeaMessageChangeCallback));
112 #endif
113 g_offFuncMap.insert(std::make_pair("locationChange", &OffLocationChangeCallback));
114 g_offFuncMap.insert(std::make_pair("countryCodeChange", &OffCountryCodeChangeCallback));
115 }
116
SubscribeLocationServiceState(const napi_env & env,const napi_ref & handlerRef,sptr<LocationSwitchCallbackNapi> & switchCallbackHost)117 void SubscribeLocationServiceState(const napi_env& env,
118 const napi_ref& handlerRef, sptr<LocationSwitchCallbackNapi>& switchCallbackHost)
119 {
120 switchCallbackHost->SetEnv(env);
121 switchCallbackHost->SetHandleCb(handlerRef);
122 g_locatorProxy->RegisterSwitchCallback(switchCallbackHost->AsObject(), DEFAULT_UID);
123 }
124
125 #ifdef ENABLE_NAPI_MANAGER
SubscribeLocationServiceStateV9(const napi_env & env,const napi_ref & handlerRef,sptr<LocationSwitchCallbackNapi> & switchCallbackHost)126 LocationErrCode SubscribeLocationServiceStateV9(const napi_env& env,
127 const napi_ref& handlerRef, sptr<LocationSwitchCallbackNapi>& switchCallbackHost)
128 {
129 switchCallbackHost->SetEnv(env);
130 switchCallbackHost->SetHandleCb(handlerRef);
131 return g_locatorProxy->RegisterSwitchCallbackV9(switchCallbackHost->AsObject());
132 }
133 #endif
134
SubscribeGnssStatus(const napi_env & env,const napi_ref & handlerRef,sptr<GnssStatusCallbackNapi> & gnssStatusCallbackHost)135 void SubscribeGnssStatus(const napi_env& env, const napi_ref& handlerRef,
136 sptr<GnssStatusCallbackNapi>& gnssStatusCallbackHost)
137 {
138 gnssStatusCallbackHost->SetEnv(env);
139 gnssStatusCallbackHost->SetHandleCb(handlerRef);
140 g_locatorProxy->RegisterGnssStatusCallback(gnssStatusCallbackHost->AsObject(), DEFAULT_UID);
141 }
142
143 #ifdef ENABLE_NAPI_MANAGER
SubscribeGnssStatusV9(const napi_env & env,const napi_ref & handlerRef,sptr<GnssStatusCallbackNapi> & gnssStatusCallbackHost)144 LocationErrCode SubscribeGnssStatusV9(const napi_env& env, const napi_ref& handlerRef,
145 sptr<GnssStatusCallbackNapi>& gnssStatusCallbackHost)
146 {
147 LocationErrCode errorCode = CheckLocationSwitchEnable();
148 if (errorCode != ERRCODE_SUCCESS) {
149 return errorCode;
150 }
151 gnssStatusCallbackHost->SetEnv(env);
152 gnssStatusCallbackHost->SetHandleCb(handlerRef);
153 return g_locatorProxy->RegisterGnssStatusCallbackV9(gnssStatusCallbackHost->AsObject());
154 }
155 #endif
156
SubscribeNmeaMessage(const napi_env & env,const napi_ref & handlerRef,sptr<NmeaMessageCallbackNapi> & nmeaMessageCallbackHost)157 void SubscribeNmeaMessage(const napi_env& env, const napi_ref& handlerRef,
158 sptr<NmeaMessageCallbackNapi>& nmeaMessageCallbackHost)
159 {
160 nmeaMessageCallbackHost->SetEnv(env);
161 nmeaMessageCallbackHost->SetHandleCb(handlerRef);
162 g_locatorProxy->RegisterNmeaMessageCallback(nmeaMessageCallbackHost->AsObject(), DEFAULT_UID);
163 }
164
165 #ifdef ENABLE_NAPI_MANAGER
SubscribeNmeaMessageV9(const napi_env & env,const napi_ref & handlerRef,sptr<NmeaMessageCallbackNapi> & nmeaMessageCallbackHost)166 LocationErrCode SubscribeNmeaMessageV9(const napi_env& env, const napi_ref& handlerRef,
167 sptr<NmeaMessageCallbackNapi>& nmeaMessageCallbackHost)
168 {
169 LocationErrCode errorCode = CheckLocationSwitchEnable();
170 if (errorCode != ERRCODE_SUCCESS) {
171 return errorCode;
172 }
173 nmeaMessageCallbackHost->SetEnv(env);
174 nmeaMessageCallbackHost->SetHandleCb(handlerRef);
175 return g_locatorProxy->RegisterNmeaMessageCallbackV9(nmeaMessageCallbackHost->AsObject());
176 }
177 #endif
178
UnSubscribeLocationServiceState(sptr<LocationSwitchCallbackNapi> & switchCallbackHost)179 void UnSubscribeLocationServiceState(sptr<LocationSwitchCallbackNapi>& switchCallbackHost)
180 {
181 LBSLOGD(LOCATION_NAPI, "UnSubscribeLocationServiceState");
182 g_locatorProxy->UnregisterSwitchCallback(switchCallbackHost->AsObject());
183 }
184
185 #ifdef ENABLE_NAPI_MANAGER
UnSubscribeLocationServiceStateV9(sptr<LocationSwitchCallbackNapi> & switchCallbackHost)186 LocationErrCode UnSubscribeLocationServiceStateV9(sptr<LocationSwitchCallbackNapi>& switchCallbackHost)
187 {
188 LBSLOGD(LOCATION_NAPI, "UnSubscribeLocationServiceStateV9");
189 return g_locatorProxy->UnregisterSwitchCallbackV9(switchCallbackHost->AsObject());
190 }
191 #endif
192
UnSubscribeGnssStatus(sptr<GnssStatusCallbackNapi> & gnssStatusCallbackHost)193 void UnSubscribeGnssStatus(sptr<GnssStatusCallbackNapi>& gnssStatusCallbackHost)
194 {
195 LBSLOGD(LOCATION_NAPI, "UnSubscribeGnssStatus");
196 g_locatorProxy->UnregisterGnssStatusCallback(gnssStatusCallbackHost->AsObject());
197 }
198
199 #ifdef ENABLE_NAPI_MANAGER
UnSubscribeGnssStatusV9(sptr<GnssStatusCallbackNapi> & gnssStatusCallbackHost)200 LocationErrCode UnSubscribeGnssStatusV9(sptr<GnssStatusCallbackNapi>& gnssStatusCallbackHost)
201 {
202 LBSLOGD(LOCATION_NAPI, "UnSubscribeGnssStatusV9");
203 return g_locatorProxy->UnregisterGnssStatusCallbackV9(gnssStatusCallbackHost->AsObject());
204 }
205 #endif
206
UnSubscribeNmeaMessage(sptr<NmeaMessageCallbackNapi> & nmeaMessageCallbackHost)207 void UnSubscribeNmeaMessage(sptr<NmeaMessageCallbackNapi>& nmeaMessageCallbackHost)
208 {
209 LBSLOGD(LOCATION_NAPI, "UnSubscribeNmeaMessage");
210 g_locatorProxy->UnregisterNmeaMessageCallback(nmeaMessageCallbackHost->AsObject());
211 }
212
213 #ifdef ENABLE_NAPI_MANAGER
UnSubscribeNmeaMessageV9(sptr<NmeaMessageCallbackNapi> & nmeaMessageCallbackHost)214 LocationErrCode UnSubscribeNmeaMessageV9(sptr<NmeaMessageCallbackNapi>& nmeaMessageCallbackHost)
215 {
216 LBSLOGD(LOCATION_NAPI, "UnSubscribeNmeaMessageV9");
217 return g_locatorProxy->UnregisterNmeaMessageCallbackV9(nmeaMessageCallbackHost->AsObject());
218 }
219 #endif
220
SubscribeLocationChange(const napi_env & env,const napi_value & object,const napi_ref & handlerRef,sptr<LocatorCallbackNapi> & locatorCallbackHost)221 void SubscribeLocationChange(const napi_env& env, const napi_value& object,
222 const napi_ref& handlerRef, sptr<LocatorCallbackNapi>& locatorCallbackHost)
223 {
224 auto locatorCallback = sptr<ILocatorCallback>(locatorCallbackHost);
225 locatorCallbackHost->SetFixNumber(0);
226 locatorCallbackHost->SetEnv(env);
227 locatorCallbackHost->SetHandleCb(handlerRef);
228 auto requestConfig = std::make_unique<RequestConfig>();
229 JsObjToLocationRequest(env, object, requestConfig);
230 g_locatorProxy->StartLocating(requestConfig, locatorCallback);
231 }
232
233 #ifdef ENABLE_NAPI_MANAGER
SubscribeLocationChangeV9(const napi_env & env,const napi_value & object,const napi_ref & handlerRef,sptr<LocatorCallbackNapi> & locatorCallbackHost)234 LocationErrCode SubscribeLocationChangeV9(const napi_env& env, const napi_value& object,
235 const napi_ref& handlerRef, sptr<LocatorCallbackNapi>& locatorCallbackHost)
236 {
237 LocationErrCode errorCode = CheckLocationSwitchEnable();
238 if (errorCode != ERRCODE_SUCCESS) {
239 return errorCode;
240 }
241 auto locatorCallback = sptr<ILocatorCallback>(locatorCallbackHost);
242 locatorCallbackHost->SetFixNumber(0);
243 locatorCallbackHost->SetEnv(env);
244 locatorCallbackHost->SetHandleCb(handlerRef);
245 auto requestConfig = std::make_unique<RequestConfig>();
246 JsObjToLocationRequest(env, object, requestConfig);
247 if (!IsRequestConfigValid(requestConfig)) {
248 return ERRCODE_INVALID_PARAM;
249 }
250 return g_locatorProxy->StartLocatingV9(requestConfig, locatorCallback);
251 }
252 #endif
253
SubscribeCountryCodeChange(const napi_env & env,const napi_ref & handlerRef,sptr<CountryCodeCallbackNapi> & callbackHost)254 void SubscribeCountryCodeChange(const napi_env& env,
255 const napi_ref& handlerRef, sptr<CountryCodeCallbackNapi>& callbackHost)
256 {
257 auto callbackPtr = sptr<ICountryCodeCallback>(callbackHost);
258 callbackHost->SetEnv(env);
259 callbackHost->SetCallback(handlerRef);
260 g_locatorProxy->RegisterCountryCodeCallback(callbackPtr->AsObject(), DEFAULT_UID);
261 }
262
263 #ifdef ENABLE_NAPI_MANAGER
SubscribeCountryCodeChangeV9(const napi_env & env,const napi_ref & handlerRef,sptr<CountryCodeCallbackNapi> & callbackHost)264 LocationErrCode SubscribeCountryCodeChangeV9(const napi_env& env,
265 const napi_ref& handlerRef, sptr<CountryCodeCallbackNapi>& callbackHost)
266 {
267 auto callbackPtr = sptr<ICountryCodeCallback>(callbackHost);
268 callbackHost->SetEnv(env);
269 callbackHost->SetCallback(handlerRef);
270 return g_locatorProxy->RegisterCountryCodeCallbackV9(callbackPtr->AsObject());
271 }
272 #endif
273
274 #ifdef ENABLE_NAPI_MANAGER
SubscribeLocatingRequiredDataChange(const napi_env & env,const napi_value & object,const napi_ref & handlerRef,sptr<LocatingRequiredDataCallbackNapi> & locatingCallbackHost)275 LocationErrCode SubscribeLocatingRequiredDataChange(const napi_env& env, const napi_value& object,
276 const napi_ref& handlerRef, sptr<LocatingRequiredDataCallbackNapi>& locatingCallbackHost)
277 {
278 auto callbackPtr = sptr<ILocatingRequiredDataCallback>(locatingCallbackHost);
279 locatingCallbackHost->SetEnv(env);
280 locatingCallbackHost->SetHandleCb(handlerRef);
281 std::unique_ptr<LocatingRequiredDataConfig> dataConfig = std::make_unique<LocatingRequiredDataConfig>();
282 JsObjToLocatingRequiredDataConfig(env, object, dataConfig);
283 return g_locatorProxy->RegisterLocatingRequiredDataCallback(dataConfig, callbackPtr);
284 }
285
SubscribeLocationError(const napi_env & env,const napi_ref & handlerRef,sptr<LocationErrorCallbackNapi> & locationErrorCallbackHost)286 LocationErrCode SubscribeLocationError(const napi_env& env,
287 const napi_ref& handlerRef, sptr<LocationErrorCallbackNapi>& locationErrorCallbackHost)
288 {
289 locationErrorCallbackHost->SetEnv(env);
290 locationErrorCallbackHost->SetHandleCb(handlerRef);
291 auto locationErrorCallback = sptr<ILocatorCallback>(locationErrorCallbackHost);
292 return g_locatorProxy->SubscribeLocationError(locationErrorCallback);
293 }
294 #endif
295
UnsubscribeCountryCodeChange(sptr<CountryCodeCallbackNapi> & callbackHost)296 void UnsubscribeCountryCodeChange(sptr<CountryCodeCallbackNapi>& callbackHost)
297 {
298 LBSLOGD(LOCATION_NAPI, "UnsubscribeCountryCodeChange");
299 g_locatorProxy->UnregisterCountryCodeCallback(callbackHost->AsObject());
300 }
301
302 #ifdef ENABLE_NAPI_MANAGER
UnsubscribeCountryCodeChangeV9(sptr<CountryCodeCallbackNapi> & callbackHost)303 LocationErrCode UnsubscribeCountryCodeChangeV9(sptr<CountryCodeCallbackNapi>& callbackHost)
304 {
305 LBSLOGD(LOCATION_NAPI, "UnsubscribeCountryCodeChangeV9");
306 return g_locatorProxy->UnregisterCountryCodeCallbackV9(callbackHost->AsObject());
307 }
308 #endif
309
SubscribeCacheLocationChange(const napi_env & env,const napi_value & object,const napi_ref & handlerRef,sptr<CachedLocationsCallbackNapi> & cachedCallbackHost)310 void SubscribeCacheLocationChange(const napi_env& env, const napi_value& object,
311 const napi_ref& handlerRef, sptr<CachedLocationsCallbackNapi>& cachedCallbackHost)
312 {
313 auto cachedCallback = sptr<ICachedLocationsCallback>(cachedCallbackHost);
314 cachedCallbackHost->SetEnv(env);
315 cachedCallbackHost->SetHandleCb(handlerRef);
316 JsObjToCachedLocationRequest(env, object, g_cachedRequest);
317 g_locatorProxy->RegisterCachedLocationCallback(g_cachedRequest, cachedCallback);
318 }
319
320 #ifdef ENABLE_NAPI_MANAGER
SubscribeCacheLocationChangeV9(const napi_env & env,const napi_value & object,const napi_ref & handlerRef,sptr<CachedLocationsCallbackNapi> & cachedCallbackHost)321 LocationErrCode SubscribeCacheLocationChangeV9(const napi_env& env, const napi_value& object,
322 const napi_ref& handlerRef, sptr<CachedLocationsCallbackNapi>& cachedCallbackHost)
323 {
324 LocationErrCode errorCode = CheckLocationSwitchEnable();
325 if (errorCode != ERRCODE_SUCCESS) {
326 return errorCode;
327 }
328 auto cachedCallback = sptr<ICachedLocationsCallback>(cachedCallbackHost);
329 cachedCallbackHost->SetEnv(env);
330 cachedCallbackHost->SetHandleCb(handlerRef);
331 JsObjToCachedLocationRequest(env, object, g_cachedRequest);
332 g_locatorProxy->RegisterCachedLocationCallbackV9(g_cachedRequest, cachedCallback);
333 return ERRCODE_NOT_SUPPORTED;
334 }
335 #endif
336
SubscribeFenceStatusChange(const napi_env & env,const napi_value & object,const napi_value & handler)337 void SubscribeFenceStatusChange(const napi_env& env, const napi_value& object, const napi_value& handler)
338 {
339 AbilityRuntime::WantAgent::WantAgent *wantAgent = nullptr;
340 napi_unwrap(env, handler, (void **)&wantAgent);
341 if (wantAgent == nullptr) {
342 LBSLOGE(LOCATION_NAPI, "wantAgent is nullptr");
343 return;
344 }
345 std::shared_ptr<GeofenceRequest> fenceRequest = std::make_shared<GeofenceRequest>();
346 fenceRequest->SetWantAgent(*wantAgent);
347 JsObjToGeoFenceRequest(env, object, fenceRequest);
348 g_geofenceProxy->AddFenceV9(fenceRequest);
349 }
350
351 #ifdef ENABLE_NAPI_MANAGER
SubscribeFenceStatusChangeV9(const napi_env & env,const napi_value & object,const napi_value & handler)352 LocationErrCode SubscribeFenceStatusChangeV9(const napi_env& env, const napi_value& object, const napi_value& handler)
353 {
354 LocationErrCode errorCode = CheckLocationSwitchEnable();
355 if (errorCode != ERRCODE_SUCCESS) {
356 return errorCode;
357 }
358 AbilityRuntime::WantAgent::WantAgent *wantAgent = nullptr;
359 napi_unwrap(env, handler, (void **)&wantAgent);
360 if (wantAgent == nullptr) {
361 LBSLOGE(LOCATION_NAPI, "wantAgent is nullptr");
362 return ERRCODE_INVALID_PARAM;
363 }
364 std::shared_ptr<GeofenceRequest> fenceRequest = std::make_shared<GeofenceRequest>();
365 fenceRequest->SetWantAgent(*wantAgent);
366 JsObjToGeoFenceRequest(env, object, fenceRequest);
367 LocationErrCode errCode = g_geofenceProxy->AddFenceV9(fenceRequest);
368 return errCode;
369 }
370 #endif
371
UnSubscribeFenceStatusChange(const napi_env & env,const napi_value & object,const napi_value & handler)372 void UnSubscribeFenceStatusChange(const napi_env& env, const napi_value& object, const napi_value& handler)
373 {
374 AbilityRuntime::WantAgent::WantAgent *wantAgent = nullptr;
375 napi_unwrap(env, handler, (void **)&wantAgent);
376 if (wantAgent == nullptr) {
377 LBSLOGE(LOCATION_NAPI, "wantAgent is nullptr");
378 return;
379 }
380 std::shared_ptr<GeofenceRequest> fenceRequest = std::make_shared<GeofenceRequest>();
381 fenceRequest->SetWantAgent(*wantAgent);
382 JsObjToGeoFenceRequest(env, object, fenceRequest);
383 g_geofenceProxy->RemoveFenceV9(fenceRequest);
384 }
385
386 #ifdef ENABLE_NAPI_MANAGER
UnSubscribeFenceStatusChangeV9(const napi_env & env,const napi_value & object,const napi_value & handler)387 LocationErrCode UnSubscribeFenceStatusChangeV9(const napi_env& env, const napi_value& object, const napi_value& handler)
388 {
389 AbilityRuntime::WantAgent::WantAgent *wantAgent = nullptr;
390 napi_unwrap(env, handler, (void **)&wantAgent);
391 if (wantAgent == nullptr) {
392 LBSLOGE(LOCATION_NAPI, "wantAgent is nullptr");
393 return ERRCODE_INVALID_PARAM;
394 }
395 std::shared_ptr<GeofenceRequest> fenceRequest = std::make_shared<GeofenceRequest>();
396 fenceRequest->SetWantAgent(*wantAgent);
397 JsObjToGeoFenceRequest(env, object, fenceRequest);
398 return g_geofenceProxy->RemoveFenceV9(fenceRequest);
399 }
400 #endif
401
402 #ifdef ENABLE_NAPI_MANAGER
UnSubscribeLocatingRequiredDataChange(sptr<LocatingRequiredDataCallbackNapi> & callbackHost)403 LocationErrCode UnSubscribeLocatingRequiredDataChange(sptr<LocatingRequiredDataCallbackNapi>& callbackHost)
404 {
405 LBSLOGD(LOCATION_NAPI, "%{public}s start", __func__);
406 auto callbackPtr = sptr<ILocatingRequiredDataCallback>(callbackHost);
407 return g_locatorProxy->UnRegisterLocatingRequiredDataCallback(callbackPtr);
408 }
409 #endif
410
GenerateExecuteContext(SingleLocationAsyncContext * context)411 void GenerateExecuteContext(SingleLocationAsyncContext* context)
412 {
413 if (context == nullptr) {
414 return;
415 }
416 auto callbackHost = context->callbackHost_;
417 if (g_locatorProxy->IsLocationEnabled() && callbackHost != nullptr) {
418 auto callbackPtr = sptr<ILocatorCallback>(callbackHost);
419 #ifdef ENABLE_NAPI_MANAGER
420 LocationErrCode errorCode = g_locatorProxy->StartLocatingV9(context->request_, callbackPtr);
421 context->errCode = errorCode;
422 if (errorCode != ERRCODE_SUCCESS) {
423 callbackHost->SetCount(0);
424 }
425 #else
426 g_locatorProxy->StartLocating(context->request_, callbackPtr);
427 #endif
428 if (context->timeout_ > DEFAULT_TIMEOUT_30S) {
429 callbackHost->Wait(DEFAULT_TIMEOUT_30S);
430 if (callbackHost->GetSingleLocation() == nullptr) {
431 callbackHost->Wait(context->timeout_ - DEFAULT_TIMEOUT_30S);
432 }
433 } else {
434 callbackHost->Wait(context->timeout_);
435 }
436 g_locatorProxy->StopLocating(callbackPtr);
437 if (callbackHost->GetCount() != 0 && callbackHost->GetSingleLocation() == nullptr) {
438 context->errCode = ERRCODE_LOCATING_FAIL;
439 }
440 callbackHost->SetCount(1);
441 #ifndef ENABLE_NAPI_MANAGER
442 } else {
443 context->errCode = LOCATION_SWITCH_ERROR;
444 #endif
445 }
446 }
447
GenerateCompleteContext(SingleLocationAsyncContext * context)448 void GenerateCompleteContext(SingleLocationAsyncContext* context)
449 {
450 if (context == nullptr) {
451 return;
452 }
453 NAPI_CALL_RETURN_VOID(context->env, napi_create_object(context->env, &context->result[PARAM1]));
454 auto callbackHost = context->callbackHost_;
455 if (callbackHost != nullptr && callbackHost->GetSingleLocation() != nullptr) {
456 std::unique_ptr<Location> location = std::make_unique<Location>(*callbackHost->GetSingleLocation());
457 LocationToJs(context->env, location, context->result[PARAM1]);
458 } else {
459 LBSLOGE(LOCATOR_STANDARD, "m_singleLocation is nullptr!");
460 }
461 if (context->callbackHost_) {
462 context->callbackHost_ = nullptr;
463 }
464 }
465
CreateSingleLocationAsyncContext(const napi_env & env,std::unique_ptr<RequestConfig> & config,sptr<LocatorCallbackNapi> callback)466 SingleLocationAsyncContext* CreateSingleLocationAsyncContext(const napi_env& env,
467 std::unique_ptr<RequestConfig>& config, sptr<LocatorCallbackNapi> callback)
468 {
469 auto asyncContext = new (std::nothrow) SingleLocationAsyncContext(env);
470 NAPI_ASSERT(env, asyncContext != nullptr, "asyncContext is null.");
471 NAPI_CALL(env, napi_create_string_latin1(env, "GetCurrentLocation",
472 NAPI_AUTO_LENGTH, &asyncContext->resourceName));
473 asyncContext->timeout_ = config->GetTimeOut();
474 asyncContext->callbackHost_ = callback;
475 asyncContext->request_ = std::move(config);
476 asyncContext->executeFunc = [&](void* data) -> void {
477 if (data == nullptr) {
478 LBSLOGE(LOCATOR_STANDARD, "data is nullptr!");
479 return;
480 }
481 auto context = static_cast<SingleLocationAsyncContext*>(data);
482 GenerateExecuteContext(context);
483 };
484 asyncContext->completeFunc = [&](void* data) -> void {
485 if (data == nullptr) {
486 LBSLOGE(LOCATOR_STANDARD, "data is nullptr!");
487 return;
488 }
489 auto context = static_cast<SingleLocationAsyncContext*>(data);
490 GenerateCompleteContext(context);
491 LBSLOGD(LOCATOR_STANDARD, "Push single location to client");
492 };
493 return asyncContext;
494 }
495
GetObjectArgsNum(const napi_env & env,const size_t argc,const napi_value * argv)496 int GetObjectArgsNum(const napi_env& env, const size_t argc, const napi_value* argv)
497 {
498 napi_valuetype valueType = napi_undefined;
499 int objectArgsNum = PARAM0;
500 if (argc == PARAM0) {
501 objectArgsNum = PARAM0;
502 } else if (argc == PARAM1) {
503 NAPI_CALL_BASE(env, napi_typeof(env, argv[PARAM0], &valueType), objectArgsNum);
504 if (valueType == napi_object) {
505 objectArgsNum = PARAM1;
506 } else if (valueType == napi_function) {
507 objectArgsNum = PARAM0;
508 }
509 } else if (argc == PARAM2) {
510 objectArgsNum = PARAM1;
511 } else {
512 LBSLOGD(LOCATION_NAPI, "argc of GetCurrentLocation is wrong.");
513 }
514 return objectArgsNum;
515 }
516
CreateRequestConfig(const napi_env & env,const napi_value * argv,const size_t & objectArgsNum)517 std::unique_ptr<RequestConfig> CreateRequestConfig(const napi_env& env,
518 const napi_value* argv, const size_t& objectArgsNum)
519 {
520 auto requestConfig = std::make_unique<RequestConfig>();
521 if (objectArgsNum > 0) {
522 JsObjToCurrentLocationRequest(env, argv[objectArgsNum - 1], requestConfig);
523 } else {
524 requestConfig->SetPriority(PRIORITY_FAST_FIRST_FIX);
525 }
526 requestConfig->SetFixNumber(1);
527 return requestConfig;
528 }
529
CreateSingleLocationCallbackHost()530 sptr<LocatorCallbackNapi> CreateSingleLocationCallbackHost()
531 {
532 auto callbackHost =
533 sptr<LocatorCallbackNapi>(new (std::nothrow) LocatorCallbackNapi());
534 if (callbackHost) {
535 callbackHost->SetFixNumber(1);
536 }
537 return callbackHost;
538 }
539
RequestLocationOnce(const napi_env & env,const size_t argc,const napi_value * argv)540 napi_value RequestLocationOnce(const napi_env& env, const size_t argc, const napi_value* argv)
541 {
542 size_t objectArgsNum = 0;
543
544 objectArgsNum = static_cast<size_t>(GetObjectArgsNum(env, argc, argv));
545 auto requestConfig = CreateRequestConfig(env, argv, objectArgsNum);
546 NAPI_ASSERT(env, requestConfig != nullptr, "requestConfig is null.");
547 auto singleLocatorCallbackHost = CreateSingleLocationCallbackHost();
548 NAPI_ASSERT(env, singleLocatorCallbackHost != nullptr, "callbackHost is null.");
549
550 auto asyncContext = CreateSingleLocationAsyncContext(env, requestConfig, singleLocatorCallbackHost);
551 NAPI_ASSERT(env, asyncContext != nullptr, "asyncContext is null.");
552 return DoAsyncWork(env, asyncContext, argc, argv, objectArgsNum);
553 }
554
555 #ifdef ENABLE_NAPI_MANAGER
RequestLocationOnceV9(const napi_env & env,const size_t argc,const napi_value * argv)556 napi_value RequestLocationOnceV9(const napi_env& env, const size_t argc, const napi_value* argv)
557 {
558 size_t objectArgsNum = 0;
559 objectArgsNum = static_cast<size_t>(GetObjectArgsNum(env, argc, argv));
560 auto requestConfig = CreateRequestConfig(env, argv, objectArgsNum);
561 if (!IsRequestConfigValid(requestConfig)) {
562 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
563 return UndefinedNapiValue(env);
564 }
565 auto singleLocatorCallbackHost = CreateSingleLocationCallbackHost();
566 if (singleLocatorCallbackHost == nullptr) {
567 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
568 return UndefinedNapiValue(env);
569 }
570 singleLocatorCallbackHost->SetLocationPriority(GetCurrentLocationType(requestConfig));
571 LocationErrCode errorCode = CheckLocationSwitchEnable();
572 if (errorCode != ERRCODE_SUCCESS) {
573 HandleSyncErrCode(env, errorCode);
574 return UndefinedNapiValue(env);
575 }
576
577 auto asyncContext = CreateSingleLocationAsyncContext(env, requestConfig, singleLocatorCallbackHost);
578 if (asyncContext == nullptr) {
579 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
580 return UndefinedNapiValue(env);
581 }
582 return DoAsyncWork(env, asyncContext, argc, argv, objectArgsNum);
583 }
584 #endif
585
UnSubscribeLocationChange(sptr<ILocatorCallback> & callback)586 void UnSubscribeLocationChange(sptr<ILocatorCallback>& callback)
587 {
588 LBSLOGD(LOCATION_NAPI, "UnSubscribeLocationChange");
589 g_locatorProxy->StopLocating(callback);
590 }
591
592 #ifdef ENABLE_NAPI_MANAGER
UnSubscribeLocationChangeV9(sptr<ILocatorCallback> & callback)593 LocationErrCode UnSubscribeLocationChangeV9(sptr<ILocatorCallback>& callback)
594 {
595 LBSLOGD(LOCATION_NAPI, "UnSubscribeLocationChangeV9");
596 return g_locatorProxy->StopLocatingV9(callback);
597 }
598 #endif
599
UnSubscribeCacheLocationChange(sptr<ICachedLocationsCallback> & callback)600 void UnSubscribeCacheLocationChange(sptr<ICachedLocationsCallback>& callback)
601 {
602 LBSLOGD(LOCATION_NAPI, "UnSubscribeCacheLocationChange");
603 g_locatorProxy->UnregisterCachedLocationCallback(callback);
604 }
605
606 #ifdef ENABLE_NAPI_MANAGER
UnSubscribeCacheLocationChangeV9(sptr<ICachedLocationsCallback> & callback)607 LocationErrCode UnSubscribeCacheLocationChangeV9(sptr<ICachedLocationsCallback>& callback)
608 {
609 LBSLOGD(LOCATION_NAPI, "UnSubscribeCacheLocationChangeV9");
610 g_locatorProxy->UnregisterCachedLocationCallbackV9(callback);
611 return ERRCODE_NOT_SUPPORTED;
612 }
613
UnSubscribeLocationError(sptr<ILocatorCallback> & callback)614 LocationErrCode UnSubscribeLocationError(sptr<ILocatorCallback>& callback)
615 {
616 LBSLOGD(LOCATION_NAPI, "UnSubscribeLocationError");
617 return g_locatorProxy->UnSubscribeLocationError(callback);
618 }
619 #endif
620
IsCallbackEquals(const napi_env & env,const napi_value & handler,const napi_ref & savedCallback)621 bool IsCallbackEquals(const napi_env& env, const napi_value& handler, const napi_ref& savedCallback)
622 {
623 napi_value handlerTemp = nullptr;
624 if (savedCallback == nullptr || handler == nullptr) {
625 return false;
626 }
627 NAPI_CALL_BASE(env, napi_get_reference_value(env, savedCallback, &handlerTemp), false);
628 bool isEqual = false;
629 NAPI_CALL_BASE(env, napi_strict_equals(env, handlerTemp, handler, &isEqual), false);
630 return isEqual;
631 }
632
OnLocationServiceStateCallback(const napi_env & env,const size_t argc,const napi_value * argv)633 bool OnLocationServiceStateCallback(const napi_env& env, const size_t argc, const napi_value* argv)
634 {
635 #ifdef ENABLE_NAPI_MANAGER
636 if (argc != PARAM2) {
637 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
638 return false;
639 }
640 if (!CheckIfParamIsFunctionType(env, argv[PARAM1])) {
641 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
642 return false;
643 }
644 #else
645 NAPI_ASSERT_BASE(env, argc == PARAM2, "number of parameters is wrong", INPUT_PARAMS_ERROR);
646 NAPI_ASSERT_BASE(env, CheckIfParamIsFunctionType(env, argv[PARAM1]),
647 "callback should be function, mismatch for param.", INPUT_PARAMS_ERROR);
648 #endif
649 if (g_switchCallbacks.IsCallbackInMap(env, argv[PARAM1])) {
650 LBSLOGE(LOCATION_NAPI, "This request already exists");
651 return false;
652 }
653 auto switchCallbackHost =
654 sptr<LocationSwitchCallbackNapi>(new (std::nothrow) LocationSwitchCallbackNapi());
655 if (switchCallbackHost != nullptr) {
656 napi_ref handlerRef = nullptr;
657 NAPI_CALL_BASE(env, napi_create_reference(env, argv[PARAM1], 1, &handlerRef), false);
658 #ifdef ENABLE_NAPI_MANAGER
659 LocationErrCode errorCode = SubscribeLocationServiceStateV9(env, handlerRef, switchCallbackHost);
660 if (errorCode != ERRCODE_SUCCESS) {
661 HandleSyncErrCode(env, errorCode);
662 return false;
663 }
664 #else
665 SubscribeLocationServiceState(env, handlerRef, switchCallbackHost);
666 #endif
667 g_switchCallbacks.AddCallback(env, handlerRef, switchCallbackHost);
668 }
669 return true;
670 }
671
OnCachedGnssLocationsReportingCallback(const napi_env & env,const size_t argc,const napi_value * argv)672 bool OnCachedGnssLocationsReportingCallback(const napi_env& env, const size_t argc, const napi_value* argv)
673 {
674 #ifdef ENABLE_NAPI_MANAGER
675 if (argc != PARAM3) {
676 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
677 return false;
678 }
679 napi_valuetype valueType;
680 NAPI_CALL_BASE(env, napi_typeof(env, argv[PARAM1], &valueType), false);
681 if (valueType != napi_object || !CheckIfParamIsFunctionType(env, argv[PARAM2])) {
682 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
683 return UndefinedNapiValue(env);
684 }
685 #else
686 NAPI_ASSERT_BASE(env, argc == PARAM3, "number of parameters is wrong", INPUT_PARAMS_ERROR);
687 NAPI_ASSERT_BASE(env, CheckIfParamIsFunctionType(env, argv[PARAM2]),
688 "callback should be function, mismatch for param.", INPUT_PARAMS_ERROR);
689 #endif
690 #ifndef ENABLE_NAPI_MANAGER
691 if (!g_locatorProxy->IsLocationEnabled()) {
692 LBSLOGE(LOCATION_NAPI, "location switch is off, just return.");
693 return false;
694 }
695 #endif
696 // the third params should be handler
697 if (g_cachedLocationCallbacks.IsCallbackInMap(env, argv[PARAM2])) {
698 LBSLOGE(LOCATION_NAPI, "This request already exists");
699 return false;
700 }
701 auto cachedCallbackHost =
702 sptr<CachedLocationsCallbackNapi>(new (std::nothrow) CachedLocationsCallbackNapi());
703 if (cachedCallbackHost != nullptr) {
704 napi_ref handlerRef = nullptr;
705 NAPI_CALL_BASE(env, napi_create_reference(env, argv[PARAM2], PARAM1, &handlerRef), false);
706 #ifdef ENABLE_NAPI_MANAGER
707 LocationErrCode errorCode = SubscribeCacheLocationChangeV9(env, argv[PARAM1], handlerRef, cachedCallbackHost);
708 if (errorCode != ERRCODE_SUCCESS) {
709 HandleSyncErrCode(env, errorCode);
710 return false;
711 }
712 #else
713 SubscribeCacheLocationChange(env, argv[PARAM1], handlerRef, cachedCallbackHost);
714 #endif
715 g_cachedLocationCallbacks.AddCallback(env, handlerRef, cachedCallbackHost);
716 }
717 return true;
718 }
719
OnGnssStatusChangeCallback(const napi_env & env,const size_t argc,const napi_value * argv)720 bool OnGnssStatusChangeCallback(const napi_env& env, const size_t argc, const napi_value* argv)
721 {
722 #ifdef ENABLE_NAPI_MANAGER
723 if (argc != PARAM2) {
724 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
725 return false;
726 }
727 if (!CheckIfParamIsFunctionType(env, argv[PARAM1])) {
728 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
729 return UndefinedNapiValue(env);
730 }
731 #else
732 NAPI_ASSERT_BASE(env, argc == PARAM2, "number of parameters is wrong", INPUT_PARAMS_ERROR);
733 NAPI_ASSERT_BASE(env, CheckIfParamIsFunctionType(env, argv[PARAM1]),
734 "callback should be function, mismatch for param.", INPUT_PARAMS_ERROR);
735 #endif
736 if (g_gnssStatusInfoCallbacks.IsCallbackInMap(env, argv[PARAM1])) {
737 LBSLOGE(LOCATION_NAPI, "This request already exists");
738 return false;
739 }
740 auto gnssCallbackHost =
741 sptr<GnssStatusCallbackNapi>(new (std::nothrow) GnssStatusCallbackNapi());
742 if (gnssCallbackHost != nullptr) {
743 napi_ref handlerRef = nullptr;
744 NAPI_CALL_BASE(env, napi_create_reference(env, argv[PARAM1], PARAM1, &handlerRef), false);
745 #ifdef ENABLE_NAPI_MANAGER
746 LocationErrCode errorCode = SubscribeGnssStatusV9(env, handlerRef, gnssCallbackHost);
747 if (errorCode != ERRCODE_SUCCESS) {
748 HandleSyncErrCode(env, errorCode);
749 return false;
750 }
751 #else
752 SubscribeGnssStatus(env, handlerRef, gnssCallbackHost);
753 #endif
754 g_gnssStatusInfoCallbacks.AddCallback(env, handlerRef, gnssCallbackHost);
755 }
756 return true;
757 }
758
OnLocationChangeCallback(const napi_env & env,const size_t argc,const napi_value * argv)759 bool OnLocationChangeCallback(const napi_env& env, const size_t argc, const napi_value* argv)
760 {
761 #ifdef SUPPORT_JSSTACK
762 HiviewDFX::ReportXPowerJsStackSysEvent(env, "GNSS_STATE");
763 #endif
764 #ifdef ENABLE_NAPI_MANAGER
765 if (argc != PARAM3) {
766 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
767 return false;
768 }
769 napi_valuetype valueType;
770 NAPI_CALL_BASE(env, napi_typeof(env, argv[PARAM1], &valueType), false);
771 if (valueType != napi_object || !CheckIfParamIsFunctionType(env, argv[PARAM2])) {
772 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
773 return false;
774 }
775 #else
776 NAPI_ASSERT_BASE(env, argc == PARAM3, "number of parameters is wrong", INPUT_PARAMS_ERROR);
777 NAPI_ASSERT_BASE(env, CheckIfParamIsFunctionType(env, argv[PARAM2]),
778 "callback should be function, mismatch for param.", INPUT_PARAMS_ERROR);
779 if (!g_locatorProxy->IsLocationEnabled()) {
780 LBSLOGE(LOCATION_NAPI, "location switch is off, just return.");
781 return false;
782 }
783 #endif
784 // the third params should be handler
785 if (g_locationCallbacks.IsCallbackInMap(env, argv[PARAM2])) {
786 LBSLOGE(LOCATION_NAPI, "This request already exists");
787 return false;
788 }
789 auto locatorCallbackHost =
790 sptr<LocatorCallbackNapi>(new (std::nothrow) LocatorCallbackNapi());
791 if (locatorCallbackHost != nullptr) {
792 napi_ref handlerRef = nullptr;
793 NAPI_CALL_BASE(env, napi_create_reference(env, argv[PARAM2], 1, &handlerRef), false);
794 // argv[1]:request params, argv[2]:handler
795 #ifdef ENABLE_NAPI_MANAGER
796 LocationErrCode errorCode = SubscribeLocationChangeV9(env, argv[PARAM1], handlerRef, locatorCallbackHost);
797 if (errorCode != ERRCODE_SUCCESS) {
798 HandleSyncErrCode(env, errorCode);
799 return false;
800 }
801 #else
802 SubscribeLocationChange(env, argv[PARAM1], handlerRef, locatorCallbackHost);
803 #endif
804 g_locationCallbacks.AddCallback(env, handlerRef, locatorCallbackHost);
805 }
806 return true;
807 }
808
OnNmeaMessageChangeCallback(const napi_env & env,const size_t argc,const napi_value * argv)809 bool OnNmeaMessageChangeCallback(const napi_env& env, const size_t argc, const napi_value* argv)
810 {
811 #ifdef ENABLE_NAPI_MANAGER
812 if (argc != PARAM2) {
813 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
814 return false;
815 }
816 if (!CheckIfParamIsFunctionType(env, argv[PARAM1])) {
817 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
818 return false;
819 }
820 #else
821 NAPI_ASSERT_BASE(env, argc == PARAM2, "number of parameters is wrong", INPUT_PARAMS_ERROR);
822 NAPI_ASSERT_BASE(env, CheckIfParamIsFunctionType(env, argv[PARAM1]),
823 "callback should be function, mismatch for param.", INPUT_PARAMS_ERROR);
824 #endif
825 if (g_nmeaCallbacks.IsCallbackInMap(env, argv[PARAM1])) {
826 LBSLOGE(LOCATION_NAPI, "This request already exists");
827 return false;
828 }
829 auto nmeaCallbackHost =
830 sptr<NmeaMessageCallbackNapi>(new (std::nothrow) NmeaMessageCallbackNapi());
831 if (nmeaCallbackHost != nullptr) {
832 napi_ref handlerRef = nullptr;
833 NAPI_CALL_BASE(env, napi_create_reference(env, argv[PARAM1], PARAM1, &handlerRef), false);
834 #ifdef ENABLE_NAPI_MANAGER
835 LocationErrCode errorCode = SubscribeNmeaMessageV9(env, handlerRef, nmeaCallbackHost);
836 if (errorCode != ERRCODE_SUCCESS) {
837 HandleSyncErrCode(env, errorCode);
838 return false;
839 }
840 #else
841 SubscribeNmeaMessage(env, handlerRef, nmeaCallbackHost);
842 #endif
843 g_nmeaCallbacks.AddCallback(env, handlerRef, nmeaCallbackHost);
844 }
845 return true;
846 }
847
OnCountryCodeChangeCallback(const napi_env & env,const size_t argc,const napi_value * argv)848 bool OnCountryCodeChangeCallback(const napi_env& env, const size_t argc, const napi_value* argv)
849 {
850 #ifdef ENABLE_NAPI_MANAGER
851 if (argc != PARAM2) {
852 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
853 return false;
854 }
855 if (!CheckIfParamIsFunctionType(env, argv[PARAM1])) {
856 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
857 return false;
858 }
859 #else
860 NAPI_ASSERT_BASE(env, argc == PARAM2, "number of parameters is wrong", INPUT_PARAMS_ERROR);
861 NAPI_ASSERT_BASE(env, CheckIfParamIsFunctionType(env, argv[PARAM1]),
862 "callback should be function, mismatch for param.", INPUT_PARAMS_ERROR);
863 #endif
864 if (g_countryCodeCallbacks.IsCallbackInMap(env, argv[PARAM1])) {
865 LBSLOGE(LOCATION_NAPI, "This request already exists");
866 return false;
867 }
868 auto callbackHost =
869 sptr<CountryCodeCallbackNapi>(new (std::nothrow) CountryCodeCallbackNapi());
870 if (callbackHost) {
871 napi_ref handlerRef = nullptr;
872 NAPI_CALL_BASE(env, napi_create_reference(env, argv[PARAM1], 1, &handlerRef), false);
873 #ifdef ENABLE_NAPI_MANAGER
874 LocationErrCode errorCode = SubscribeCountryCodeChangeV9(env, handlerRef, callbackHost);
875 if (errorCode != ERRCODE_SUCCESS) {
876 HandleSyncErrCode(env, errorCode);
877 return false;
878 }
879 #else
880 SubscribeCountryCodeChange(env, handlerRef, callbackHost);
881 #endif
882 g_countryCodeCallbacks.AddCallback(env, handlerRef, callbackHost);
883 }
884 return true;
885 }
886
OnFenceStatusChangeCallback(const napi_env & env,const size_t argc,const napi_value * argv)887 bool OnFenceStatusChangeCallback(const napi_env& env, const size_t argc, const napi_value* argv)
888 {
889 #ifdef ENABLE_NAPI_MANAGER
890 if (argc != PARAM3) {
891 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
892 return false;
893 }
894 #else
895 NAPI_ASSERT_BASE(env, argc == PARAM3, "number of parameters is wrong", INPUT_PARAMS_ERROR);
896 if (!g_locatorProxy->IsLocationEnabled()) {
897 LBSLOGE(LOCATION_NAPI, "location switch is off, just return.");
898 return false;
899 }
900 #endif
901 // the third params should be handler
902 #ifdef ENABLE_NAPI_MANAGER
903 LocationErrCode errorCode = SubscribeFenceStatusChangeV9(env, argv[PARAM1], argv[PARAM2]);
904 if (errorCode != ERRCODE_SUCCESS) {
905 HandleSyncErrCode(env, errorCode);
906 return false;
907 }
908 #else
909 SubscribeFenceStatusChange(env, argv[PARAM1], argv[PARAM2]);
910 #endif
911 return true;
912 }
913
914 #ifdef ENABLE_NAPI_MANAGER
OnLocatingRequiredDataChangeCallback(const napi_env & env,const size_t argc,const napi_value * argv)915 bool OnLocatingRequiredDataChangeCallback(const napi_env& env, const size_t argc, const napi_value* argv)
916 {
917 if (argc != PARAM3) {
918 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
919 return false;
920 }
921 if (!CheckIfParamIsFunctionType(env, argv[PARAM2])) {
922 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
923 return false;
924 }
925 if (g_locatingRequiredDataCallbacks.IsCallbackInMap(env, argv[PARAM2])) {
926 LBSLOGE(LOCATION_NAPI, "%{public}s, This request already exists", __func__);
927 return false;
928 }
929 auto locatingCallbackHost =
930 sptr<LocatingRequiredDataCallbackNapi>(new (std::nothrow) LocatingRequiredDataCallbackNapi());
931 if (locatingCallbackHost != nullptr) {
932 napi_ref handlerRef = nullptr;
933 NAPI_CALL_BASE(env, napi_create_reference(env, argv[PARAM2], 1, &handlerRef), false);
934
935 LocationErrCode errorCode =
936 SubscribeLocatingRequiredDataChange(env, argv[PARAM1], handlerRef, locatingCallbackHost);
937 if (errorCode != ERRCODE_SUCCESS) {
938 HandleSyncErrCode(env, errorCode);
939 return false;
940 }
941 g_locatingRequiredDataCallbacks.AddCallback(env, handlerRef, locatingCallbackHost);
942 }
943 return true;
944 }
945 #endif
946
On(napi_env env,napi_callback_info cbinfo)947 napi_value On(napi_env env, napi_callback_info cbinfo)
948 {
949 InitOnFuncMap();
950 size_t argc = MAXIMUM_JS_PARAMS;
951 napi_value argv[MAXIMUM_JS_PARAMS] = {0};
952 napi_value thisVar = nullptr;
953 LBSLOGD(LOCATION_NAPI, "On function entry");
954 NAPI_CALL(env, napi_get_cb_info(env, cbinfo, &argc, argv, &thisVar, nullptr));
955 napi_valuetype eventName = napi_undefined;
956 NAPI_CALL(env, napi_typeof(env, argv[PARAM0], &eventName));
957 #ifdef ENABLE_NAPI_MANAGER
958 if (eventName != napi_string) {
959 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
960 return UndefinedNapiValue(env);
961 }
962 #else
963 NAPI_ASSERT(env, eventName == napi_string, "type mismatch for parameter 1");
964 #endif
965 NAPI_ASSERT(env, g_locatorProxy != nullptr, "locator instance is null.");
966
967 char type[64] = {0}; // max length
968 size_t typeLen = 0;
969 NAPI_CALL(env, napi_get_value_string_utf8(env, argv[PARAM0], type, sizeof(type), &typeLen));
970 std::string event = type;
971 LBSLOGD(LOCATION_NAPI, "Subscribe event: %{public}s", event.c_str());
972 std::unique_lock<std::mutex> lock(g_FuncMapMutex);
973 auto onCallbackFunc = g_onFuncMap.find(event);
974 if (onCallbackFunc != g_onFuncMap.end() && onCallbackFunc->second != nullptr) {
975 auto memberFunc = onCallbackFunc->second;
976 (*memberFunc)(env, argc, argv);
977 }
978 return UndefinedNapiValue(env);
979 }
980
OffAllLocationServiceStateCallback(const napi_env & env)981 bool OffAllLocationServiceStateCallback(const napi_env& env)
982 {
983 std::map<napi_env, std::map<napi_ref, sptr<LocationSwitchCallbackNapi>>> callbackMap =
984 g_switchCallbacks.GetCallbackMap();
985 auto iter = callbackMap.find(env);
986 if (iter == callbackMap.end()) {
987 return false;
988 }
989 for (auto innerIter = iter->second.begin(); innerIter != iter->second.end(); innerIter++) {
990 auto callbackHost = innerIter->second;
991 if (callbackHost == nullptr) {
992 continue;
993 }
994 #ifdef ENABLE_NAPI_MANAGER
995 LocationErrCode errorCode = UnSubscribeLocationServiceStateV9(callbackHost);
996 if (errorCode != ERRCODE_SUCCESS) {
997 HandleSyncErrCode(env, errorCode);
998 return false;
999 }
1000 #else
1001 UnSubscribeLocationServiceState(callbackHost);
1002 #endif
1003 callbackHost->DeleteHandler();
1004 callbackHost = nullptr;
1005 }
1006 g_switchCallbacks.DeleteCallbackByEnv(env);
1007 return true;
1008 }
1009
OffAllLocationChangeCallback(const napi_env & env)1010 bool OffAllLocationChangeCallback(const napi_env& env)
1011 {
1012 std::map<napi_env, std::map<napi_ref, sptr<LocatorCallbackNapi>>> callbackMap =
1013 g_locationCallbacks.GetCallbackMap();
1014 auto iter = callbackMap.find(env);
1015 if (iter == callbackMap.end()) {
1016 return false;
1017 }
1018 for (auto innerIter = iter->second.begin(); innerIter != iter->second.end(); innerIter++) {
1019 auto callbackHost = innerIter->second;
1020 if (callbackHost == nullptr) {
1021 continue;
1022 }
1023 auto locatorCallback = sptr<ILocatorCallback>(callbackHost);
1024 #ifdef ENABLE_NAPI_MANAGER
1025 LocationErrCode errorCode = UnSubscribeLocationChangeV9(locatorCallback);
1026 if (errorCode != ERRCODE_SUCCESS) {
1027 HandleSyncErrCode(env, errorCode);
1028 return false;
1029 }
1030 #else
1031 UnSubscribeLocationChange(locatorCallback);
1032 #endif
1033 callbackHost->DeleteAllCallbacks();
1034 callbackHost = nullptr;
1035 }
1036 g_locationCallbacks.DeleteCallbackByEnv(env);
1037 return true;
1038 }
1039
OffAllGnssStatusChangeCallback(const napi_env & env)1040 bool OffAllGnssStatusChangeCallback(const napi_env& env)
1041 {
1042 std::map<napi_env, std::map<napi_ref, sptr<GnssStatusCallbackNapi>>> callbackMap =
1043 g_gnssStatusInfoCallbacks.GetCallbackMap();
1044 auto iter = callbackMap.find(env);
1045 if (iter == callbackMap.end()) {
1046 return false;
1047 }
1048 for (auto innerIter = iter->second.begin(); innerIter != iter->second.end(); innerIter++) {
1049 auto callbackHost = innerIter->second;
1050 if (callbackHost == nullptr) {
1051 continue;
1052 }
1053 #ifdef ENABLE_NAPI_MANAGER
1054 LocationErrCode errorCode = UnSubscribeGnssStatusV9(callbackHost);
1055 if (errorCode != ERRCODE_SUCCESS) {
1056 HandleSyncErrCode(env, errorCode);
1057 return false;
1058 }
1059 #else
1060 UnSubscribeGnssStatus(callbackHost);
1061 #endif
1062 callbackHost->DeleteHandler();
1063 callbackHost = nullptr;
1064 }
1065 g_gnssStatusInfoCallbacks.DeleteCallbackByEnv(env);
1066 return true;
1067 }
1068
OffAllNmeaMessageChangeCallback(const napi_env & env)1069 bool OffAllNmeaMessageChangeCallback(const napi_env& env)
1070 {
1071 std::map<napi_env, std::map<napi_ref, sptr<NmeaMessageCallbackNapi>>> callbackMap =
1072 g_nmeaCallbacks.GetCallbackMap();
1073 auto iter = callbackMap.find(env);
1074 if (iter == callbackMap.end()) {
1075 return false;
1076 }
1077 for (auto innerIter = iter->second.begin(); innerIter != iter->second.end(); innerIter++) {
1078 auto callbackHost = innerIter->second;
1079 if (callbackHost == nullptr) {
1080 continue;
1081 }
1082 #ifdef ENABLE_NAPI_MANAGER
1083 LocationErrCode errorCode = UnSubscribeNmeaMessageV9(callbackHost);
1084 if (errorCode != ERRCODE_SUCCESS) {
1085 HandleSyncErrCode(env, errorCode);
1086 return false;
1087 }
1088 #else
1089 UnSubscribeNmeaMessage(callbackHost);
1090 #endif
1091 callbackHost->DeleteHandler();
1092 callbackHost = nullptr;
1093 }
1094 g_nmeaCallbacks.DeleteCallbackByEnv(env);
1095 return true;
1096 }
1097
OffAllCachedGnssLocationsReportingCallback(const napi_env & env)1098 bool OffAllCachedGnssLocationsReportingCallback(const napi_env& env)
1099 {
1100 std::map<napi_env, std::map<napi_ref, sptr<CachedLocationsCallbackNapi>>> callbackMap =
1101 g_cachedLocationCallbacks.GetCallbackMap();
1102 auto iter = callbackMap.find(env);
1103 if (iter == callbackMap.end()) {
1104 #ifdef ENABLE_NAPI_MANAGER
1105 HandleSyncErrCode(env, ERRCODE_NOT_SUPPORTED);
1106 #endif
1107 return false;
1108 }
1109 for (auto innerIter = iter->second.begin(); innerIter != iter->second.end(); innerIter++) {
1110 auto callbackHost = innerIter->second;
1111 if (callbackHost == nullptr) {
1112 continue;
1113 }
1114 auto cachedCallback = sptr<ICachedLocationsCallback>(callbackHost);
1115 #ifdef ENABLE_NAPI_MANAGER
1116 LocationErrCode errorCode = UnSubscribeCacheLocationChangeV9(cachedCallback);
1117 if (errorCode != ERRCODE_SUCCESS) {
1118 HandleSyncErrCode(env, errorCode);
1119 return false;
1120 }
1121 #else
1122 UnSubscribeCacheLocationChange(cachedCallback);
1123 #endif
1124 callbackHost->DeleteHandler();
1125 callbackHost = nullptr;
1126 }
1127 g_cachedLocationCallbacks.DeleteCallbackByEnv(env);
1128 return true;
1129 }
1130
OffAllCountryCodeChangeCallback(const napi_env & env)1131 bool OffAllCountryCodeChangeCallback(const napi_env& env)
1132 {
1133 std::map<napi_env, std::map<napi_ref, sptr<CountryCodeCallbackNapi>>> callbackMap =
1134 g_countryCodeCallbacks.GetCallbackMap();
1135 auto iter = callbackMap.find(env);
1136 if (iter == callbackMap.end()) {
1137 return false;
1138 }
1139 for (auto innerIter = iter->second.begin(); innerIter != iter->second.end(); innerIter++) {
1140 auto callbackHost = innerIter->second;
1141 if (callbackHost == nullptr) {
1142 continue;
1143 }
1144 #ifdef ENABLE_NAPI_MANAGER
1145 LocationErrCode errorCode = UnsubscribeCountryCodeChangeV9(callbackHost);
1146 if (errorCode != ERRCODE_SUCCESS) {
1147 HandleSyncErrCode(env, errorCode);
1148 return false;
1149 }
1150 #else
1151 UnsubscribeCountryCodeChange(callbackHost);
1152 #endif
1153 callbackHost->DeleteHandler();
1154 callbackHost = nullptr;
1155 }
1156 g_countryCodeCallbacks.DeleteCallbackByEnv(env);
1157 return true;
1158 }
1159
1160 #ifdef ENABLE_NAPI_MANAGER
OffAllLocatingRequiredDataChangeCallback(const napi_env & env)1161 bool OffAllLocatingRequiredDataChangeCallback(const napi_env& env)
1162 {
1163 std::map<napi_env, std::map<napi_ref, sptr<LocatingRequiredDataCallbackNapi>>> callbackMap =
1164 g_locatingRequiredDataCallbacks.GetCallbackMap();
1165 auto iter = callbackMap.find(env);
1166 if (iter == callbackMap.end()) {
1167 return false;
1168 }
1169 for (auto innerIter = iter->second.begin(); innerIter != iter->second.end(); innerIter++) {
1170 auto callbackHost = innerIter->second;
1171 if (callbackHost == nullptr) {
1172 continue;
1173 }
1174 LocationErrCode errorCode = UnSubscribeLocatingRequiredDataChange(callbackHost);
1175 if (errorCode != ERRCODE_SUCCESS) {
1176 HandleSyncErrCode(env, errorCode);
1177 return false;
1178 }
1179 callbackHost->DeleteHandler();
1180 callbackHost = nullptr;
1181 }
1182 g_locatingRequiredDataCallbacks.DeleteCallbackByEnv(env);
1183 return true;
1184 }
1185 #endif
1186
OffLocationServiceStateCallback(const napi_env & env,const napi_value & handler)1187 bool OffLocationServiceStateCallback(const napi_env& env, const napi_value& handler)
1188 {
1189 auto switchCallbackHost = g_switchCallbacks.GetCallbackPtr(env, handler);
1190 if (switchCallbackHost) {
1191 #ifdef ENABLE_NAPI_MANAGER
1192 LocationErrCode errorCode = UnSubscribeLocationServiceStateV9(switchCallbackHost);
1193 if (errorCode != ERRCODE_SUCCESS) {
1194 HandleSyncErrCode(env, errorCode);
1195 return false;
1196 }
1197 #else
1198 UnSubscribeLocationServiceState(switchCallbackHost);
1199 #endif
1200 g_switchCallbacks.DeleteCallback(env, handler);
1201 switchCallbackHost->DeleteHandler();
1202 switchCallbackHost = nullptr;
1203 return true;
1204 }
1205 return false;
1206 }
1207
OffLocationChangeCallback(const napi_env & env,const napi_value & handler)1208 bool OffLocationChangeCallback(const napi_env& env, const napi_value& handler)
1209 {
1210 auto locatorCallbackHost = g_locationCallbacks.GetCallbackPtr(env, handler);
1211 if (locatorCallbackHost) {
1212 auto locatorCallback = sptr<ILocatorCallback>(locatorCallbackHost);
1213 #ifdef ENABLE_NAPI_MANAGER
1214 LocationErrCode errorCode = UnSubscribeLocationChangeV9(locatorCallback);
1215 if (errorCode != ERRCODE_SUCCESS) {
1216 HandleSyncErrCode(env, errorCode);
1217 return false;
1218 }
1219 #else
1220 UnSubscribeLocationChange(locatorCallback);
1221 #endif
1222 g_locationCallbacks.DeleteCallback(env, handler);
1223 locatorCallbackHost->DeleteAllCallbacks();
1224 locatorCallbackHost = nullptr;
1225 return true;
1226 }
1227 return false;
1228 }
1229
OffGnssStatusChangeCallback(const napi_env & env,const napi_value & handler)1230 bool OffGnssStatusChangeCallback(const napi_env& env, const napi_value& handler)
1231 {
1232 auto gnssCallbackHost = g_gnssStatusInfoCallbacks.GetCallbackPtr(env, handler);
1233 if (gnssCallbackHost) {
1234 #ifdef ENABLE_NAPI_MANAGER
1235 LocationErrCode errorCode = UnSubscribeGnssStatusV9(gnssCallbackHost);
1236 if (errorCode != ERRCODE_SUCCESS) {
1237 HandleSyncErrCode(env, errorCode);
1238 return false;
1239 }
1240 #else
1241 UnSubscribeGnssStatus(gnssCallbackHost);
1242 #endif
1243 g_gnssStatusInfoCallbacks.DeleteCallback(env, handler);
1244 gnssCallbackHost->DeleteHandler();
1245 gnssCallbackHost = nullptr;
1246 return true;
1247 }
1248 return false;
1249 }
1250
OffNmeaMessageChangeCallback(const napi_env & env,const napi_value & handler)1251 bool OffNmeaMessageChangeCallback(const napi_env& env, const napi_value& handler)
1252 {
1253 auto nmeaCallbackHost = g_nmeaCallbacks.GetCallbackPtr(env, handler);
1254 if (nmeaCallbackHost) {
1255 #ifdef ENABLE_NAPI_MANAGER
1256 LocationErrCode ret = UnSubscribeNmeaMessageV9(nmeaCallbackHost);
1257 if (ret != ERRCODE_SUCCESS) {
1258 HandleSyncErrCode(env, ret);
1259 return false;
1260 }
1261 #else
1262 UnSubscribeNmeaMessage(nmeaCallbackHost);
1263 #endif
1264 g_nmeaCallbacks.DeleteCallback(env, handler);
1265 nmeaCallbackHost->DeleteHandler();
1266 nmeaCallbackHost = nullptr;
1267 return true;
1268 }
1269 return false;
1270 }
1271
OffCachedGnssLocationsReportingCallback(const napi_env & env,const napi_value & handler)1272 bool OffCachedGnssLocationsReportingCallback(const napi_env& env, const napi_value& handler)
1273 {
1274 auto cachedCallbackHost = g_cachedLocationCallbacks.GetCallbackPtr(env, handler);
1275 if (cachedCallbackHost) {
1276 auto cachedCallback = sptr<ICachedLocationsCallback>(cachedCallbackHost);
1277 #ifdef ENABLE_NAPI_MANAGER
1278 LocationErrCode errorCode = UnSubscribeCacheLocationChangeV9(cachedCallback);
1279 if (errorCode != ERRCODE_SUCCESS) {
1280 HandleSyncErrCode(env, errorCode);
1281 return false;
1282 }
1283 #else
1284 UnSubscribeCacheLocationChange(cachedCallback);
1285 #endif
1286 g_cachedLocationCallbacks.DeleteCallback(env, handler);
1287 cachedCallbackHost->DeleteHandler();
1288 cachedCallbackHost = nullptr;
1289 return true;
1290 } else {
1291 LBSLOGI(LOCATION_NAPI, "%{public}s, the callback is not in the map", __func__);
1292 #ifdef ENABLE_NAPI_MANAGER
1293 HandleSyncErrCode(env, ERRCODE_NOT_SUPPORTED);
1294 #endif
1295 }
1296 return false;
1297 }
1298
OffCountryCodeChangeCallback(const napi_env & env,const napi_value & handler)1299 bool OffCountryCodeChangeCallback(const napi_env& env, const napi_value& handler)
1300 {
1301 auto callbackHost = g_countryCodeCallbacks.GetCallbackPtr(env, handler);
1302 if (callbackHost) {
1303 #ifdef ENABLE_NAPI_MANAGER
1304 LocationErrCode errorCode = UnsubscribeCountryCodeChangeV9(callbackHost);
1305 if (errorCode != ERRCODE_SUCCESS) {
1306 HandleSyncErrCode(env, errorCode);
1307 return false;
1308 }
1309 #else
1310 UnsubscribeCountryCodeChange(callbackHost);
1311 #endif
1312 g_countryCodeCallbacks.DeleteCallback(env, handler);
1313 callbackHost->DeleteHandler();
1314 callbackHost = nullptr;
1315 return true;
1316 }
1317 return false;
1318 }
1319
1320 #ifdef ENABLE_NAPI_MANAGER
OffLocatingRequiredDataChangeCallback(const napi_env & env,const napi_value & handler)1321 bool OffLocatingRequiredDataChangeCallback(const napi_env& env, const napi_value& handler)
1322 {
1323 auto callbackHost = g_locatingRequiredDataCallbacks.GetCallbackPtr(env, handler);
1324 if (callbackHost) {
1325 LocationErrCode errorCode = UnSubscribeLocatingRequiredDataChange(callbackHost);
1326 if (errorCode != ERRCODE_SUCCESS) {
1327 HandleSyncErrCode(env, errorCode);
1328 return false;
1329 }
1330 g_locatingRequiredDataCallbacks.DeleteCallback(env, handler);
1331 callbackHost->DeleteHandler();
1332 callbackHost = nullptr;
1333 return true;
1334 }
1335 return false;
1336 }
1337 #endif
1338
VerifyOffFuncParam(napi_env env,napi_callback_info cbinfo,size_t & argc)1339 bool VerifyOffFuncParam(napi_env env, napi_callback_info cbinfo, size_t& argc)
1340 {
1341 napi_value argv[MAXIMUM_JS_PARAMS] = {0};
1342 napi_valuetype valueType[PARAM3] = {napi_undefined};
1343 napi_value thisVar = nullptr;
1344 NAPI_CALL_BASE(env, napi_get_cb_info(env, cbinfo, &argc, argv, &thisVar, nullptr), false);
1345 NAPI_ASSERT_BASE(env, g_locatorProxy != nullptr, "locator instance is null.", false);
1346 argc = (argc > PARAM3) ? PARAM3 : argc;
1347 if (argc > 0) {
1348 for (int i = (int)(argc - 1); i >= 0; i--) {
1349 NAPI_CALL_BASE(env, napi_typeof(env, argv[i], &valueType[i]), false);
1350 /* If the type of the last input parameter is incorrect, ignore it. */
1351 if (valueType[i] != napi_function && valueType[i] != napi_object && valueType[i] != napi_string &&
1352 i == (int)(argc - 1)) {
1353 argc--;
1354 }
1355 }
1356 }
1357 if (argc == PARAM3 && valueType[argc - 1] != napi_object) {
1358 argc--;
1359 }
1360 if (argc == PARAM2 && valueType[argc - 1] != napi_function) {
1361 argc--;
1362 }
1363 if (argc < PARAM1 || valueType[PARAM0] != napi_string ||
1364 (argc == PARAM2 && valueType[PARAM1] != napi_function) ||
1365 (argc == PARAM3 && valueType[PARAM1] != napi_object && valueType[PARAM2] != napi_object)) {
1366 #ifdef ENABLE_NAPI_MANAGER
1367 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
1368 #else
1369 NAPI_ASSERT_BASE(env, false, "ERRCODE_INVALID_PARAM", false);
1370 #endif
1371 return false;
1372 }
1373 return true;
1374 }
1375
Off(napi_env env,napi_callback_info cbinfo)1376 napi_value Off(napi_env env, napi_callback_info cbinfo)
1377 {
1378 LBSLOGD(LOCATION_NAPI, "Off function entry");
1379 InitOffFuncMap();
1380
1381 size_t argc = MAXIMUM_JS_PARAMS;
1382 napi_value argv[MAXIMUM_JS_PARAMS] = {0};
1383 napi_value thisVar = nullptr;
1384 NAPI_CALL(env, napi_get_cb_info(env, cbinfo, &argc, argv, &thisVar, nullptr));
1385
1386 if (!VerifyOffFuncParam(env, cbinfo, argc)) {
1387 LBSLOGE(LOCATION_NAPI, "VerifyOffFuncParam fail");
1388 return UndefinedNapiValue(env);
1389 }
1390
1391 char type[64] = {0};
1392 size_t typeLen = 0;
1393 NAPI_CALL(env, napi_get_value_string_utf8(env, argv[PARAM0], type, sizeof(type), &typeLen));
1394 std::string event = type;
1395 LBSLOGD(LOCATION_NAPI, "Unsubscribe event: %{public}s", event.c_str());
1396 if (argc == PARAM1) {
1397 std::unique_lock<std::mutex> lock(g_FuncMapMutex);
1398 auto offAllCallbackFunc = g_offAllFuncMap.find(event);
1399 if (offAllCallbackFunc != g_offAllFuncMap.end() && offAllCallbackFunc->second != nullptr) {
1400 auto memberFunc = offAllCallbackFunc->second;
1401 (*memberFunc)(env);
1402 }
1403 } else if (argc == PARAM2) {
1404 std::unique_lock<std::mutex> lock(g_FuncMapMutex);
1405 auto offCallbackFunc = g_offFuncMap.find(event);
1406 if (offCallbackFunc != g_offFuncMap.end() && offCallbackFunc->second != nullptr) {
1407 auto singleMemberFunc = offCallbackFunc->second;
1408 (*singleMemberFunc)(env, argv[PARAM1]);
1409 }
1410 #ifdef ENABLE_NAPI_MANAGER
1411 } else if (argc == PARAM3 && event == "gnssFenceStatusChange") {
1412 LocationErrCode errorCode = UnSubscribeFenceStatusChangeV9(env, argv[PARAM1], argv[PARAM2]);
1413 if (errorCode != ERRCODE_SUCCESS) {
1414 HandleSyncErrCode(env, errorCode);
1415 }
1416 } else {
1417 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
1418 #else
1419 } else if (argc == PARAM3 && event == "fenceStatusChange") {
1420 UnSubscribeFenceStatusChange(env, argv[PARAM1], argv[PARAM2]);
1421 #endif
1422 }
1423 return UndefinedNapiValue(env);
1424 }
1425
GetCurrentLocation(napi_env env,napi_callback_info cbinfo)1426 napi_value GetCurrentLocation(napi_env env, napi_callback_info cbinfo)
1427 {
1428 size_t argc = MAXIMUM_JS_PARAMS;
1429 napi_value argv[MAXIMUM_JS_PARAMS] = {0};
1430 napi_valuetype valueType[MAXIMUM_JS_PARAMS] = {napi_undefined};
1431 napi_value thisVar = nullptr;
1432 NAPI_CALL(env, napi_get_cb_info(env, cbinfo, &argc, argv, &thisVar, nullptr));
1433 NAPI_ASSERT(env, g_locatorProxy != nullptr, "locator instance is null.");
1434 LBSLOGD(LOCATION_NAPI, "GetCurrentLocation enter");
1435 #ifdef SUPPORT_JSSTACK
1436 HiviewDFX::ReportXPowerJsStackSysEvent(env, "GNSS_STATE");
1437 #endif
1438 argc = (argc > PARAM2) ? PARAM2 : argc;
1439 if (argc > 0) {
1440 for (int i = (int)(argc - 1); i >= 0; i--) {
1441 NAPI_CALL(env, napi_typeof(env, argv[i], &valueType[i]));
1442 /* If the type of the last input parameter is incorrect, ignore it. */
1443 if (valueType[i] != napi_function && valueType[i] != napi_object &&
1444 i == (int)(argc - 1)) {
1445 argc--;
1446 }
1447 }
1448 }
1449 if (argc == PARAM2) {
1450 if (valueType[PARAM1] != napi_function) {
1451 argc--;
1452 }
1453 #ifdef ENABLE_NAPI_MANAGER
1454 else if (valueType[PARAM0] != napi_object) {
1455 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
1456 return UndefinedNapiValue(env);
1457 }
1458 #else
1459 else {
1460 NAPI_ASSERT(env, valueType[PARAM0] == napi_object, "type mismatch for parameter 1");
1461 }
1462 #endif
1463 }
1464 if (argc == PARAM1) {
1465 if (valueType[PARAM0] != napi_function && valueType[PARAM0] != napi_object) {
1466 argc--;
1467 }
1468 }
1469 #ifdef ENABLE_NAPI_MANAGER
1470 return RequestLocationOnceV9(env, argc, argv);
1471 #else
1472 return RequestLocationOnce(env, argc, argv);
1473 #endif
1474 }
1475
1476 #ifdef ENABLE_NAPI_MANAGER
CheckLocationSwitchEnable()1477 LocationErrCode CheckLocationSwitchEnable()
1478 {
1479 bool isEnabled = false;
1480 LocationErrCode errorCode = g_locatorProxy->IsLocationEnabledV9(isEnabled);
1481 if (errorCode != ERRCODE_SUCCESS) {
1482 return errorCode;
1483 }
1484 if (!isEnabled) {
1485 return ERRCODE_SWITCH_OFF;
1486 }
1487 return ERRCODE_SUCCESS;
1488 }
1489 #endif
1490
IsRequestConfigValid(std::unique_ptr<RequestConfig> & config)1491 bool IsRequestConfigValid(std::unique_ptr<RequestConfig>& config)
1492 {
1493 if (config == nullptr) {
1494 return false;
1495 }
1496 if ((config->GetScenario() > SCENE_NO_POWER || config->GetScenario() < SCENE_UNSET) &&
1497 (config->GetScenario() > LOCATION_SCENE_DAILY_LIFE_SERVICE ||
1498 config->GetScenario() < LOCATION_SCENE_NAVIGATION) &&
1499 (config->GetScenario() > LOCATION_SCENE_NO_POWER_CONSUMPTION ||
1500 config->GetScenario() < LOCATION_SCENE_HIGH_POWER_CONSUMPTION)) {
1501 return false;
1502 }
1503 if ((config->GetPriority() > PRIORITY_FAST_FIRST_FIX || config->GetPriority() < PRIORITY_UNSET) &&
1504 (config->GetPriority() > LOCATION_PRIORITY_LOCATING_SPEED ||
1505 config->GetPriority() < LOCATION_PRIORITY_ACCURACY)) {
1506 return false;
1507 }
1508 if (config->GetTimeOut() < MIN_TIMEOUTMS_FOR_LOCATIONONCE) {
1509 return false;
1510 }
1511 if (config->GetTimeInterval() < 0) {
1512 return false;
1513 }
1514 if (config->GetDistanceInterval() < 0) {
1515 return false;
1516 }
1517 if (config->GetMaxAccuracy() < 0) {
1518 return false;
1519 }
1520 return true;
1521 }
1522
1523 #ifdef ENABLE_NAPI_MANAGER
OnLocationErrorCallback(const napi_env & env,const size_t argc,const napi_value * argv)1524 bool OnLocationErrorCallback(const napi_env& env, const size_t argc, const napi_value* argv)
1525 {
1526 if (argc != PARAM2) {
1527 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
1528 LBSLOGE(LOCATION_NAPI, "ERRCODE_INVALID_PARAM");
1529 return false;
1530 }
1531 if (!CheckIfParamIsFunctionType(env, argv[PARAM1])) {
1532 HandleSyncErrCode(env, ERRCODE_INVALID_PARAM);
1533 LBSLOGE(LOCATION_NAPI, "ERRCODE_INVALID_PARAM");
1534 return false;
1535 }
1536 // the third params should be handler
1537 if (g_locationErrorCallbackHosts.IsCallbackInMap(env, argv[PARAM1])) {
1538 LBSLOGE(LOCATION_NAPI, "This request already exists");
1539 return false;
1540 }
1541 auto locationErrorCallbackHost =
1542 sptr<LocationErrorCallbackNapi>(new (std::nothrow) LocationErrorCallbackNapi());
1543 if (locationErrorCallbackHost != nullptr) {
1544 napi_ref handlerRef = nullptr;
1545 NAPI_CALL_BASE(env, napi_create_reference(env, argv[PARAM1], 1, &handlerRef), false);
1546 // argv[1]:request params, argv[2]:handler
1547 LocationErrCode errorCode = SubscribeLocationError(env, handlerRef, locationErrorCallbackHost);
1548 if (errorCode != ERRCODE_SUCCESS) {
1549 HandleSyncErrCode(env, errorCode);
1550 return false;
1551 }
1552 g_locationErrorCallbackHosts.AddCallback(env, handlerRef, locationErrorCallbackHost);
1553 }
1554 return true;
1555 }
1556
OffLocationErrorCallback(const napi_env & env,const napi_value & handler)1557 bool OffLocationErrorCallback(const napi_env& env, const napi_value& handler)
1558 {
1559 auto locationErrorCallbackHost = g_locationErrorCallbackHosts.GetCallbackPtr(env, handler);
1560 if (locationErrorCallbackHost) {
1561 auto locatorCallback = sptr<ILocatorCallback>(locationErrorCallbackHost);
1562 LocationErrCode errorCode = UnSubscribeLocationError(locatorCallback);
1563 if (errorCode != ERRCODE_SUCCESS) {
1564 HandleSyncErrCode(env, errorCode);
1565 return false;
1566 }
1567 g_locationErrorCallbackHosts.DeleteCallback(env, handler);
1568 locationErrorCallbackHost = nullptr;
1569 return true;
1570 }
1571 return false;
1572 }
1573 #endif
1574
GetCurrentLocationType(std::unique_ptr<RequestConfig> & config)1575 int GetCurrentLocationType(std::unique_ptr<RequestConfig>& config)
1576 {
1577 if (config->GetPriority() == LOCATION_PRIORITY_ACCURACY ||
1578 (config->GetScenario() == SCENE_UNSET && config->GetPriority() == PRIORITY_ACCURACY) ||
1579 config->GetScenario() == SCENE_NAVIGATION ||
1580 config->GetScenario() == SCENE_TRAJECTORY_TRACKING ||
1581 config->GetScenario() == SCENE_CAR_HAILING) {
1582 return LOCATION_PRIORITY_ACCURACY;
1583 } else {
1584 return LOCATION_PRIORITY_LOCATING_SPEED;
1585 }
1586 }
1587 } // namespace Location
1588 } // namespace OHOS
1589