• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2023-2023 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  * Description: supply untils realization for napi interface.
15  * Author: zhangjingnan
16  * Create: 2022-7-11
17  */
18 
19 #include <uv.h>
20 #include <memory>
21 #include "securec.h"
22 #include "napi/native_api.h"
23 #include "napi/native_node_api.h"
24 #include "cast_engine_log.h"
25 #include "cast_engine_common.h"
26 #include "napi_cast_session.h"
27 #include "napi_castengine_utils.h"
28 
29 using namespace std;
30 using namespace OHOS::CastEngine;
31 
32 namespace OHOS {
33 namespace CastEngine {
34 namespace CastEngineClient {
35 DEFINE_CAST_ENGINE_LABEL("Cast-Napi-Utils");
36 
GetUndefinedValue(napi_env env)37 napi_value GetUndefinedValue(napi_env env)
38 {
39     napi_value result {};
40     napi_get_undefined(env, &result);
41     return result;
42 }
43 
ParseString(napi_env env,napi_value args)44 string ParseString(napi_env env, napi_value args)
45 {
46     string result {};
47     if (args == nullptr) {
48         CLOGE("args is nullptr");
49         return result;
50     }
51     napi_valuetype valueType;
52     napi_status status = napi_typeof(env, args, &valueType);
53     CLOGD("param=%{public}d.", valueType);
54     if (status != napi_ok || valueType != napi_string) {
55         CLOGE("Wrong argument type. String expected.");
56         result = "";
57         return result;
58     }
59     size_t size = 0;
60     size_t bufSize = 0;
61 
62     if (napi_get_value_string_utf8(env, args, nullptr, bufSize, &size) != napi_ok) {
63         CLOGE("can not get string size");
64         result = "";
65         return result;
66     }
67     result.reserve(size + 1);
68     result.resize(size);
69     if (napi_get_value_string_utf8(env, args, result.data(), (size + 1), &size) != napi_ok) {
70         CLOGE("can not get string value");
71         result = "";
72         return result;
73     }
74     return result;
75 }
76 
ParseInt32(napi_env env,napi_value args)77 int32_t ParseInt32(napi_env env, napi_value args)
78 {
79     int32_t param = 0;
80     if (args == nullptr) {
81         CLOGE("args is nullptr");
82         return param;
83     }
84     napi_valuetype valueType;
85     napi_status status = napi_typeof(env, args, &valueType);
86     if (status != napi_ok) {
87         CLOGE("napi_typeof failed.");
88         return param;
89     }
90     CLOGD("param=%{public}d.", valueType);
91     if (valueType != napi_number) {
92         CLOGE("Wrong argument type. Int32 expected.");
93         return param;
94     }
95     status = napi_get_value_int32(env, args, &param);
96     if (status != napi_ok) {
97         CLOGE("napi_get_value_int32 failed.");
98         return param;
99     }
100     return param;
101 }
102 
ParseUint32(napi_env env,napi_value args)103 uint32_t ParseUint32(napi_env env, napi_value args)
104 {
105     uint32_t param = 0;
106     if (args == nullptr) {
107         CLOGE("args is nullptr");
108         return param;
109     }
110     napi_valuetype valueType;
111     napi_status status = napi_typeof(env, args, &valueType);
112     if (status != napi_ok) {
113         CLOGE("napi_typeof failed.");
114         return param;
115     }
116     CLOGD("param=%{public}d.", valueType);
117     if (valueType != napi_number) {
118         CLOGE("Wrong argument type. Int32 expected.");
119         return param;
120     }
121     status = napi_get_value_uint32(env, args, &param);
122     if (status != napi_ok) {
123         CLOGE("napi_get_value_int32 failed.");
124         return param;
125     }
126     return param;
127 }
128 
ParseBool(napi_env env,napi_value args)129 bool ParseBool(napi_env env, napi_value args)
130 {
131     bool param = false;
132     if (args == nullptr) {
133         CLOGE("args is nullptr");
134         return param;
135     }
136     napi_valuetype valueType;
137     napi_status status = napi_typeof(env, args, &valueType);
138     if (status != napi_ok) {
139         CLOGE("napi_typeof failed.");
140         return param;
141     }
142 
143     CLOGD("param=%{public}d.", valueType);
144     if (valueType != napi_boolean) {
145         CLOGE("Wrong argument type. bool expected.");
146         return param;
147     }
148     status = napi_get_value_bool(env, args, &param);
149     if (status != napi_ok) {
150         CLOGE("napi_get_value_bool failed.");
151         return param;
152     }
153     return param;
154 }
155 
ConvertDeviceListToJS(napi_env env,const vector<CastRemoteDevice> & devices)156 napi_value ConvertDeviceListToJS(napi_env env, const vector<CastRemoteDevice> &devices)
157 {
158     int count = 0;
159     napi_value devicesList = nullptr;
160     NAPI_CALL(env, napi_create_array(env, &devicesList));
161     for (CastRemoteDevice vec : devices) {
162         napi_value deviceResult = ConvertCastRemoteDeviceToJS(env, vec);
163         NAPI_CALL(env, napi_set_element(env, devicesList, count, deviceResult));
164         count++;
165     }
166 
167     if (devicesList == nullptr) {
168         CLOGE("devicesList is null");
169     }
170     return devicesList;
171 }
172 
ConvertDeviceStateInfoToJS(napi_env env,const DeviceStateInfo & stateEvent)173 napi_value ConvertDeviceStateInfoToJS(napi_env env, const DeviceStateInfo &stateEvent)
174 {
175     napi_value stateEventCallback = nullptr;
176     NAPI_CALL(env, napi_create_object(env, &stateEventCallback));
177 
178     napi_value deviceState = nullptr;
179     NAPI_CALL(env, napi_create_int32(env, static_cast<int32_t>(stateEvent.deviceState), &deviceState));
180     NAPI_CALL(env, napi_set_named_property(env, stateEventCallback, "deviceState", deviceState));
181 
182     napi_value deviceId = nullptr;
183     NAPI_CALL(env, napi_create_string_utf8(env, stateEvent.deviceId.c_str(), NAPI_AUTO_LENGTH, &deviceId));
184     NAPI_CALL(env, napi_set_named_property(env, stateEventCallback, "deviceId", deviceId));
185 
186     napi_value reasonCode = nullptr;
187     NAPI_CALL(env, napi_create_int32(env, static_cast<int32_t>(stateEvent.reasonCode), &reasonCode));
188     NAPI_CALL(env, napi_set_named_property(env, stateEventCallback, "reasonCode", reasonCode));
189 
190     return stateEventCallback;
191 }
192 
GetCastRemoteDeviceFromJS(napi_env env,napi_value & object)193 CastRemoteDevice GetCastRemoteDeviceFromJS(napi_env env, napi_value &object)
194 {
195     CastRemoteDevice castRemoteDevice = CastRemoteDevice();
196 
197     castRemoteDevice.deviceId = JsObjectToString(env, object, "deviceId");
198     castRemoteDevice.deviceName = JsObjectToString(env, object, "deviceName");
199     int32_t deviceTypeCallback = JsObjectToInt32(env, object, "deviceType");
200     DeviceType deviceType = static_cast<DeviceType>(deviceTypeCallback);
201     int32_t subDeviceTypeCallback = JsObjectToInt32(env, object, "subDeviceType");
202     SubDeviceType subDeviceType = static_cast<SubDeviceType>(subDeviceTypeCallback);
203     castRemoteDevice.ipAddress = JsObjectToString(env, object, "ipAddress");
204     int32_t channelTypeInt = JsObjectToInt32(env, object, "channelType");
205     ChannelType channelType = static_cast<ChannelType>(channelTypeInt);
206     castRemoteDevice.networkId = JsObjectToString(env, object, "networkId");
207     castRemoteDevice.deviceType = deviceType;
208     castRemoteDevice.subDeviceType = subDeviceType;
209     castRemoteDevice.channelType = channelType;
210     return castRemoteDevice;
211 }
212 
GetWindowPropertyFromJS(napi_env env,napi_value & object)213 WindowProperty GetWindowPropertyFromJS(napi_env env, napi_value &object)
214 {
215     WindowProperty windowProperty = WindowProperty();
216 
217     napi_value windowPropertyCallback = nullptr;
218     bool hasProperty = false;
219     napi_status status = napi_has_named_property(env, object, "windowProperty", &hasProperty);
220     if (status == napi_ok && hasProperty) {
221         status = napi_get_named_property(env, object, "windowProperty", &windowPropertyCallback);
222         if (status != napi_ok) {
223             CLOGE("napi_get_named_property failed.");
224             return windowProperty;
225         }
226         uint32_t width = JsObjectToUint32(env, windowPropertyCallback, "width");
227         uint32_t height = JsObjectToUint32(env, windowPropertyCallback, "height");
228         uint32_t startX = JsObjectToUint32(env, windowPropertyCallback, "startX");
229         uint32_t startY = JsObjectToUint32(env, windowPropertyCallback, "startY");
230 
231         windowProperty.startX = startX;
232         windowProperty.startY = startY;
233         windowProperty.width = width;
234         windowProperty.height = height;
235     }
236     return windowProperty;
237 }
238 
GetProtocolTypesFromJS(napi_env env,napi_value & object,int & protocolTypes)239 bool GetProtocolTypesFromJS(napi_env env, napi_value &object, int &protocolTypes)
240 {
241     bool isArray = false;
242     NAPI_CALL_BASE(env, napi_is_array(env, object, &isArray), false);
243     if (!isArray) {
244         CLOGE("protocolType is not array.");
245         return false;
246     }
247     uint32_t arrLen = 0;
248     NAPI_CALL_BASE(env, napi_get_array_length(env, object, &arrLen), false);
249     if (arrLen == 0) {
250         CLOGE("mediaInfoList len is invalid");
251         return false;
252     }
253     uint32_t ret = 0;
254     for (uint32_t i = 0; i < arrLen; i++) {
255         napi_value item = nullptr;
256         NAPI_CALL_BASE(env, napi_get_element(env, object, i, &item), false);
257         ret = ret | static_cast<uint32_t>(ParseInt32(env, item));
258     }
259     protocolTypes = static_cast<int>(ret);
260     CLOGI("GetProtocolTypesFromJS finished, protocolTypes: %{public}d", protocolTypes);
261     return true;
262 }
263 
GetMediaInfoHolderFromJS(napi_env env,napi_value & object,MediaInfoHolder & mediaInfoHolder)264 bool GetMediaInfoHolderFromJS(napi_env env, napi_value &object, MediaInfoHolder &mediaInfoHolder)
265 {
266     napi_value mediaInfoList = nullptr;
267     bool hasProperty = false;
268 
269     mediaInfoHolder.currentIndex = JsObjectToUint32(env, object, "currentIndex");
270     mediaInfoHolder.progressRefreshInterval = JsObjectToUint32(env, object, "progressRefreshInterval");
271     NAPI_CALL_BASE(env, napi_has_named_property(env, object, "mediaInfoList", &hasProperty), false);
272     if (!hasProperty) {
273         CLOGE("mediaInfoList is not exit");
274         return false;
275     }
276     NAPI_CALL_BASE(env, napi_get_named_property(env, object, "mediaInfoList", &mediaInfoList), false);
277     bool isArray = false;
278     NAPI_CALL_BASE(env, napi_is_array(env, mediaInfoList, &isArray), false);
279     if (!isArray) {
280         CLOGE("mediaInfoList is not array.");
281         return false;
282     }
283     uint32_t arrLen = 0;
284     NAPI_CALL_BASE(env, napi_get_array_length(env, mediaInfoList, &arrLen), false);
285     if (arrLen == 0) {
286         CLOGE("mediaInfoList len is invalid");
287         return false;
288     }
289     for (uint32_t i = 0; i < arrLen; i++) {
290         napi_value item = nullptr;
291         NAPI_CALL_BASE(env, napi_get_element(env, mediaInfoList, i, &item), false);
292         MediaInfo mediaInfo = MediaInfo{};
293         GetMediaInfoFromJS(env, item, mediaInfo);
294         mediaInfoHolder.mediaInfoList.push_back(mediaInfo);
295     }
296     return true;
297 }
298 
GetMediaInfoFromJS(napi_env env,napi_value & object,MediaInfo & mediaInfo)299 bool GetMediaInfoFromJS(napi_env env, napi_value &object, MediaInfo &mediaInfo)
300 {
301     mediaInfo.mediaId = JsObjectToString(env, object, "mediaId");
302     mediaInfo.mediaName = JsObjectToString(env, object, "mediaName");
303     mediaInfo.mediaUrl = JsObjectToString(env, object, "mediaUrl");
304     mediaInfo.mediaType = JsObjectToString(env, object, "mediaType");
305     mediaInfo.albumCoverUrl = JsObjectToString(env, object, "albumCoverUrl");
306     mediaInfo.albumTitle = JsObjectToString(env, object, "albumTitle");
307     mediaInfo.mediaArtist = JsObjectToString(env, object, "mediaArtist");
308     mediaInfo.lrcUrl = JsObjectToString(env, object, "lrcUrl");
309     mediaInfo.lrcContent = JsObjectToString(env, object, "lrcContent");
310     mediaInfo.appIconUrl = JsObjectToString(env, object, "appIconUrl");
311     mediaInfo.appName = JsObjectToString(env, object, "appName");
312     mediaInfo.mediaSize = JsObjectToUint32(env, object, "mediaSize");
313     mediaInfo.startPosition = JsObjectToUint32(env, object, "startPosition");
314     mediaInfo.duration = JsObjectToUint32(env, object, "duration");
315     mediaInfo.closingCreditsPosition = JsObjectToUint32(env, object, "closingCreditsPosition");
316     return true;
317 }
318 
GetCastSessionPropertyFromJS(napi_env env,napi_value & object)319 CastSessionProperty GetCastSessionPropertyFromJS(napi_env env, napi_value &object)
320 {
321     CastSessionProperty castSessionProperty = CastSessionProperty();
322 
323     int32_t protocolTypeInt = JsObjectToInt32(env, object, "protocolType");
324     ProtocolType protocolType = static_cast<ProtocolType>(protocolTypeInt);
325     int32_t endTypeInt = JsObjectToInt32(env, object, "endType");
326     EndType endType = static_cast<EndType>(endTypeInt);
327     napi_value audioPropertyCallback = nullptr;
328     bool hasProperty = false;
329     napi_status status = napi_has_named_property(env, object, "audioProperty", &hasProperty);
330     if (status == napi_ok && hasProperty) {
331         status = napi_get_named_property(env, object, "audioProperty", &audioPropertyCallback);
332         if (status != napi_ok) {
333             CLOGE("napi_get_named_property failed.");
334             return castSessionProperty;
335         }
336         AudioProperty audioProperty = GetAudioPropertyFromJS(env, audioPropertyCallback);
337         castSessionProperty.audioProperty = audioProperty;
338     }
339 
340     napi_value videoPropertyCallback = nullptr;
341     hasProperty = false;
342     status = napi_has_named_property(env, object, "videoProperty", &hasProperty);
343     if (status == napi_ok && hasProperty) {
344         status = napi_get_named_property(env, object, "videoProperty", &videoPropertyCallback);
345         if (status != napi_ok) {
346             CLOGE("napi_get_named_property failed.");
347             return castSessionProperty;
348         }
349         VideoProperty videoProperty = GetVideoPropertyFromJS(env, videoPropertyCallback);
350         castSessionProperty.videoProperty = videoProperty;
351     }
352     WindowProperty windowProperty = GetWindowPropertyFromJS(env, object);
353 
354     castSessionProperty.protocolType = protocolType;
355     castSessionProperty.endType = endType;
356     castSessionProperty.windowProperty = windowProperty;
357     return castSessionProperty;
358 }
359 
GetAudioPropertyFromJS(napi_env env,napi_value & object)360 AudioProperty GetAudioPropertyFromJS(napi_env env, napi_value &object)
361 {
362     AudioProperty audioProperty = AudioProperty();
363 
364     uint32_t sampleRate = JsObjectToUint32(env, object, "sampleRate");
365     uint32_t channelConfig = JsObjectToUint32(env, object, "channelConfig");
366     uint32_t bitrate = JsObjectToUint32(env, object, "bitrate");
367     uint32_t codec = JsObjectToUint32(env, object, "codec");
368 
369     audioProperty.sampleRate = sampleRate;
370     audioProperty.channelConfig = channelConfig;
371     audioProperty.bitrate = bitrate;
372     audioProperty.codec = codec;
373     return audioProperty;
374 }
375 
GetVideoPropertyFromJS(napi_env env,napi_value & object)376 VideoProperty GetVideoPropertyFromJS(napi_env env, napi_value &object)
377 {
378     VideoProperty videoProperty = VideoProperty();
379     uint32_t videoWidth = JsObjectToUint32(env, object, "videoWidth");
380     uint32_t videoHeight = JsObjectToUint32(env, object, "videoHeight");
381     uint32_t fps = JsObjectToUint32(env, object, "fps");
382     int32_t codecTypeInt = JsObjectToInt32(env, object, "codecType");
383     VideoCodecType codecType = static_cast<VideoCodecType>(codecTypeInt);
384     uint32_t gop = JsObjectToUint32(env, object, "gop");
385     uint32_t bitrate = JsObjectToUint32(env, object, "bitrate");
386     uint32_t minBitrate = JsObjectToUint32(env, object, "minBitrate");
387     uint32_t maxBitrate = JsObjectToUint32(env, object, "maxBitrate");
388     uint32_t dpi = JsObjectToUint32(env, object, "dpi");
389     int32_t colorStandardInt = JsObjectToInt32(env, object, "colorStandard");
390     ColorStandard colorStandard = static_cast<ColorStandard>(colorStandardInt);
391     uint32_t screenWidth = JsObjectToUint32(env, object, "screenWidth");
392     uint32_t screenHeight = JsObjectToUint32(env, object, "screenHeight");
393     uint32_t profile = JsObjectToUint32(env, object, "profile");
394     uint32_t level = JsObjectToUint32(env, object, "level");
395 
396     videoProperty.videoWidth = videoWidth;
397     videoProperty.videoHeight = videoHeight;
398     videoProperty.fps = fps;
399     videoProperty.codecType = codecType;
400     videoProperty.gop = gop;
401     videoProperty.bitrate = bitrate;
402     videoProperty.minBitrate = minBitrate;
403     videoProperty.maxBitrate = maxBitrate;
404     videoProperty.dpi = dpi;
405     videoProperty.colorStandard = colorStandard;
406     videoProperty.screenWidth = screenWidth;
407     videoProperty.screenHeight = screenHeight;
408     videoProperty.profile = profile;
409     videoProperty.level = level;
410     return videoProperty;
411 }
412 
Equals(napi_env env,napi_value value,napi_ref copy)413 bool Equals(napi_env env, napi_value value, napi_ref copy)
414 {
415     if (copy == nullptr) {
416         return (value == nullptr);
417     }
418 
419     napi_value copyValue = nullptr;
420     if (napi_get_reference_value(env, copy, &copyValue) != napi_ok) {
421         CLOGE("get ref value failed");
422         return false;
423     }
424     bool isEquals = false;
425     if (napi_strict_equals(env, value, copyValue, &isEquals) != napi_ok) {
426         CLOGE("get equals result failed");
427         return false;
428     }
429     return isEquals;
430 }
431 
GetRefByCallback(napi_env env,std::list<napi_ref> & callbackList,napi_value callback,napi_ref & callbackRef)432 napi_status GetRefByCallback(napi_env env, std::list<napi_ref> &callbackList,
433     napi_value callback, napi_ref &callbackRef)
434 {
435     for (auto ref = callbackList.begin(); ref != callbackList.end(); ++ref) {
436         if (Equals(env, callback, *ref)) {
437             CLOGD("Callback has been matched");
438             callbackRef = *ref;
439             break;
440         }
441     }
442     return napi_ok;
443 }
444 
ConvertCastRemoteDeviceToJS(napi_env env,const CastRemoteDevice & castRemoteDevice)445 napi_value ConvertCastRemoteDeviceToJS(napi_env env, const CastRemoteDevice &castRemoteDevice)
446 {
447     napi_value result = nullptr;
448     NAPI_CALL(env, napi_create_object(env, &result));
449     napi_value deviceId = nullptr;
450     NAPI_CALL(env, napi_create_string_utf8(env, castRemoteDevice.deviceId.c_str(), NAPI_AUTO_LENGTH, &deviceId));
451     NAPI_CALL(env, napi_set_named_property(env, result, "deviceId", deviceId));
452     napi_value deviceName = nullptr;
453     CLOGD("ConvertCastRemoteDeviceToJS deviceName %{public}s", castRemoteDevice.deviceName.c_str());
454     NAPI_CALL(env, napi_create_string_utf8(env, castRemoteDevice.deviceName.c_str(), NAPI_AUTO_LENGTH, &deviceName));
455     NAPI_CALL(env, napi_set_named_property(env, result, "deviceName", deviceName));
456     napi_value deviceType = nullptr;
457     NAPI_CALL(env, napi_create_int32(env, static_cast<int32_t>(castRemoteDevice.deviceType), &deviceType));
458     NAPI_CALL(env, napi_set_named_property(env, result, "deviceType", deviceType));
459     napi_value subDeviceType = nullptr;
460     NAPI_CALL(env, napi_create_int32(env, static_cast<int32_t>(castRemoteDevice.subDeviceType), &subDeviceType));
461     NAPI_CALL(env, napi_set_named_property(env, result, "subDeviceType", subDeviceType));
462     napi_value ipAddress = nullptr;
463     NAPI_CALL(env, napi_create_string_utf8(env, castRemoteDevice.ipAddress.c_str(), NAPI_AUTO_LENGTH, &ipAddress));
464     NAPI_CALL(env, napi_set_named_property(env, result, "ipAddress", ipAddress));
465     napi_value channelType = nullptr;
466     NAPI_CALL(env, napi_create_int32(env, static_cast<int32_t>(castRemoteDevice.channelType), &channelType));
467     NAPI_CALL(env, napi_set_named_property(env, result, "channelType", channelType));
468     napi_value networkId = nullptr;
469     NAPI_CALL(env, napi_create_string_utf8(env, castRemoteDevice.networkId.c_str(), NAPI_AUTO_LENGTH, &networkId));
470     NAPI_CALL(env, napi_set_named_property(env, result, "networkId", networkId));
471     napi_value isLeagacy = nullptr;
472     NAPI_CALL(env, napi_get_boolean(env, castRemoteDevice.isLeagacy, &isLeagacy));
473     NAPI_CALL(env, napi_set_named_property(env, result, "isLeagacy", isLeagacy));
474     napi_value mediumTypes = nullptr;
475     NAPI_CALL(env, napi_create_int32(env, static_cast<int32_t>(castRemoteDevice.mediumTypes), &mediumTypes));
476     NAPI_CALL(env, napi_set_named_property(env, result, "mediumTypes", mediumTypes));
477     napi_value protocolCapabilities = nullptr;
478     NAPI_CALL(env,
479         napi_create_int32(env, static_cast<int32_t>(castRemoteDevice.protocolCapabilities), &protocolCapabilities));
480     NAPI_CALL(env, napi_set_named_property(env, result, "protocolCapabilities", protocolCapabilities));
481     return result;
482 }
483 
JsObjectToString(napi_env env,napi_value & object,const char * fieldStr)484 string JsObjectToString(napi_env env, napi_value &object, const char *fieldStr)
485 {
486     string fieldRef {};
487     if (object == nullptr) {
488         CLOGE("args is nullptr");
489         return fieldRef;
490     }
491     napi_value field = nullptr;
492     bool hasProperty = false;
493 
494     napi_status status = napi_has_named_property(env, object, fieldStr, &hasProperty);
495     if (status == napi_ok && hasProperty) {
496         status = napi_get_named_property(env, object, fieldStr, &field);
497         if (status != napi_ok) {
498             CLOGE("napi_get_named_property failed.");
499             return fieldRef;
500         }
501         fieldRef = ParseString(env, field);
502         return fieldRef;
503     } else {
504         CLOGE("Js obj to str no property: %{public}s", fieldStr);
505     }
506     return fieldRef;
507 }
508 
JsObjectToInt32(napi_env env,napi_value & object,const char * fieldStr)509 int32_t JsObjectToInt32(napi_env env, napi_value &object, const char *fieldStr)
510 {
511     int32_t fieldRef = 0;
512     if (object == nullptr) {
513         CLOGE("args is nullptr");
514         return fieldRef;
515     }
516     bool hasProperty = false;
517     napi_status status = napi_has_named_property(env, object, fieldStr, &hasProperty);
518     if (status == napi_ok && hasProperty) {
519         napi_value field;
520         napi_valuetype valueType;
521         status = napi_get_named_property(env, object, fieldStr, &field);
522         if (status != napi_ok) {
523             CLOGE("napi_get_named_property failed.");
524             return fieldRef;
525         }
526         status = napi_typeof(env, field, &valueType);
527         if (status != napi_ok || valueType != napi_number) {
528             CLOGE("Wrong argument type. Number expected.");
529             return fieldRef;
530         }
531         status = napi_get_value_int32(env, field, &fieldRef);
532         if (status != napi_ok) {
533             CLOGE("napi_get_value_int32 failed");
534             return fieldRef;
535         }
536         return fieldRef;
537     } else {
538         CLOGE("Js to int32_t no property: %{public}s", fieldStr);
539     }
540     return fieldRef;
541 }
542 
JsObjectToBool(napi_env env,napi_value & object,const char * fieldStr)543 bool JsObjectToBool(napi_env env, napi_value &object, const char *fieldStr)
544 {
545     bool fieldRef = false;
546     if (object == nullptr) {
547         CLOGE("args is nullptr");
548         return fieldRef;
549     }
550     bool hasProperty = false;
551     napi_status status = napi_has_named_property(env, object, fieldStr, &hasProperty);
552     if (status == napi_ok && hasProperty) {
553         napi_value field;
554         napi_valuetype valueType;
555         status = napi_get_named_property(env, object, fieldStr, &field);
556         if (status != napi_ok) {
557             CLOGE("napi_get_named_property failed.");
558             return fieldRef;
559         }
560         status = napi_typeof(env, field, &valueType);
561         if (status != napi_ok || valueType != napi_boolean) {
562             CLOGE("Wrong argument type. Bool expected.");
563             return fieldRef;
564         }
565         status = napi_get_value_bool(env, field, &fieldRef);
566         if (status != napi_ok) {
567             CLOGE("napi_get_value_bool failed");
568             return fieldRef;
569         }
570         return fieldRef;
571     } else {
572         CLOGE("Js to bool no property: %{public}s", fieldStr);
573     }
574     return fieldRef;
575 }
576 
JsObjectToUint32(napi_env env,napi_value & object,const char * fieldStr)577 uint32_t JsObjectToUint32(napi_env env, napi_value &object, const char *fieldStr)
578 {
579     uint32_t fieldRef = 0;
580     if (object == nullptr) {
581         CLOGE("args is nullptr");
582         return fieldRef;
583     }
584     bool hasProperty = false;
585     napi_status status = napi_has_named_property(env, object, fieldStr, &hasProperty);
586     if (status == napi_ok && hasProperty) {
587         napi_value field;
588         napi_valuetype valueType;
589         status = napi_get_named_property(env, object, fieldStr, &field);
590         if (status != napi_ok) {
591             CLOGE("napi_get_named_property failed.");
592             return fieldRef;
593         }
594         status = napi_typeof(env, field, &valueType);
595         if (status != napi_ok || valueType != napi_number) {
596             CLOGE("Wrong argument type. Number expected.");
597             return fieldRef;
598         }
599         status = napi_get_value_uint32(env, field, &fieldRef);
600         if (status != napi_ok) {
601             CLOGE("napi_get_value_uint32 failed");
602             return fieldRef;
603         }
604         return fieldRef;
605     } else {
606         CLOGE("Js to uint32_t no property: %{public}s", fieldStr);
607     }
608     return fieldRef;
609 }
610 
JsObjectToDouble(napi_env env,napi_value & object,const char * fieldStr)611 double JsObjectToDouble(napi_env env, napi_value &object, const char *fieldStr)
612 {
613     double fieldRef = 0;
614     if (object == nullptr) {
615         CLOGE("args is nullptr");
616         return fieldRef;
617     }
618     bool hasProperty = false;
619     napi_status status = napi_has_named_property(env, object, fieldStr, &hasProperty);
620     if (status == napi_ok && hasProperty) {
621         napi_value field;
622         napi_valuetype valueType;
623         status = napi_get_named_property(env, object, fieldStr, &field);
624         if (status != napi_ok) {
625             CLOGE("napi_get_named_property failed.");
626             return fieldRef;
627         }
628         status = napi_typeof(env, field, &valueType);
629         if (status != napi_ok || valueType != napi_number) {
630             CLOGE("Wrong argument type. Number expected.");
631             return fieldRef;
632         }
633         status = napi_get_value_double(env, field, &fieldRef);
634         if (status != napi_ok) {
635             CLOGE("napi_get_value_double failed");
636             return fieldRef;
637         }
638         return fieldRef;
639     } else {
640         CLOGE("Js to double no property: %{public}s", fieldStr);
641     }
642     return fieldRef;
643 }
644 
JsObjectToInt64(napi_env env,napi_value & object,const char * fieldStr)645 int64_t JsObjectToInt64(napi_env env, napi_value &object, const char *fieldStr)
646 {
647     int64_t fieldRef = 0;
648     if (object == nullptr) {
649         CLOGE("args is nullptr");
650         return fieldRef;
651     }
652     bool hasProperty = false;
653     napi_status status = napi_has_named_property(env, object, fieldStr, &hasProperty);
654     if (status == napi_ok && hasProperty) {
655         napi_value field;
656         napi_valuetype valueType;
657         status = napi_get_named_property(env, object, fieldStr, &field);
658         if (status != napi_ok) {
659             CLOGE("napi_get_named_property failed");
660             return fieldRef;
661         }
662         status = napi_typeof(env, field, &valueType);
663         if (status != napi_ok || valueType != napi_number) {
664             CLOGE("Wrong argument type. Number expected.");
665             return fieldRef;
666         }
667         status = napi_get_value_int64(env, field, &fieldRef);
668         if (status != napi_ok) {
669             CLOGE("napi_get_value_int64 failed");
670             return fieldRef;
671         }
672         return fieldRef;
673     } else {
674         CLOGE("Js to int64_t no property: %{public}s", fieldStr);
675     }
676     return fieldRef;
677 }
678 
ConvertMediaInfoToJS(napi_env env,const MediaInfo & mediaInfo)679 napi_value ConvertMediaInfoToJS(napi_env env, const MediaInfo &mediaInfo)
680 {
681     CLOGD("ConvertMediaInfoToJS start");
682     napi_value result = nullptr;
683     napi_value value = nullptr;
684     NAPI_CALL(env, napi_create_object(env, &result));
685     NAPI_CALL(env, napi_create_string_utf8(env, mediaInfo.mediaId.c_str(), NAPI_AUTO_LENGTH, &value));
686     NAPI_CALL(env, napi_set_named_property(env, result, "mediaId", value));
687     NAPI_CALL(env, napi_create_string_utf8(env, mediaInfo.mediaName.c_str(), NAPI_AUTO_LENGTH, &value));
688     NAPI_CALL(env, napi_set_named_property(env, result, "mediaName", value));
689     NAPI_CALL(env, napi_create_string_utf8(env, mediaInfo.mediaUrl.c_str(), NAPI_AUTO_LENGTH, &value));
690     NAPI_CALL(env, napi_set_named_property(env, result, "mediaUrl", value));
691     NAPI_CALL(env, napi_create_string_utf8(env, mediaInfo.mediaType.c_str(), NAPI_AUTO_LENGTH, &value));
692     NAPI_CALL(env, napi_set_named_property(env, result, "mediaType", value));
693     NAPI_CALL(env, napi_create_string_utf8(env, mediaInfo.albumCoverUrl.c_str(), NAPI_AUTO_LENGTH, &value));
694     NAPI_CALL(env, napi_set_named_property(env, result, "albumCoverUrl", value));
695     NAPI_CALL(env, napi_create_string_utf8(env, mediaInfo.albumTitle.c_str(), NAPI_AUTO_LENGTH, &value));
696     NAPI_CALL(env, napi_set_named_property(env, result, "albumTitle", value));
697     NAPI_CALL(env, napi_create_string_utf8(env, mediaInfo.mediaArtist.c_str(), NAPI_AUTO_LENGTH, &value));
698     NAPI_CALL(env, napi_set_named_property(env, result, "mediaArtist", value));
699     NAPI_CALL(env, napi_create_string_utf8(env, mediaInfo.lrcUrl.c_str(), NAPI_AUTO_LENGTH, &value));
700     NAPI_CALL(env, napi_set_named_property(env, result, "lrcUrl", value));
701     NAPI_CALL(env, napi_create_string_utf8(env, mediaInfo.lrcContent.c_str(), NAPI_AUTO_LENGTH, &value));
702     NAPI_CALL(env, napi_set_named_property(env, result, "lrcContent", value));
703     NAPI_CALL(env, napi_create_string_utf8(env, mediaInfo.appIconUrl.c_str(), NAPI_AUTO_LENGTH, &value));
704     NAPI_CALL(env, napi_set_named_property(env, result, "appIconUrl", value));
705     NAPI_CALL(env, napi_create_string_utf8(env, mediaInfo.appName.c_str(), NAPI_AUTO_LENGTH, &value));
706     NAPI_CALL(env, napi_set_named_property(env, result, "appName", value));
707 
708     NAPI_CALL(env, napi_create_uint32(env, mediaInfo.mediaSize, &value));
709     NAPI_CALL(env, napi_set_named_property(env, result, "mediaSize", value));
710     NAPI_CALL(env, napi_create_uint32(env, mediaInfo.startPosition, &value));
711     NAPI_CALL(env, napi_set_named_property(env, result, "startPosition", value));
712     NAPI_CALL(env, napi_create_uint32(env, mediaInfo.duration, &value));
713     NAPI_CALL(env, napi_set_named_property(env, result, "duration", value));
714     NAPI_CALL(env, napi_create_uint32(env, mediaInfo.closingCreditsPosition, &value));
715     NAPI_CALL(env, napi_set_named_property(env, result, "closingCreditsPosition", value));
716     CLOGD("ConvertMediaInfoToJS end");
717 
718     return result;
719 }
720 
ConvertMediaInfoHolderToJS(napi_env env,const MediaInfoHolder & mediaInfoHolder)721 napi_value ConvertMediaInfoHolderToJS(napi_env env, const MediaInfoHolder &mediaInfoHolder)
722 {
723     CLOGD("ConvertMediaInfoHolderToJS start");
724     napi_value result = nullptr;
725     napi_value value = nullptr;
726     size_t len = mediaInfoHolder.mediaInfoList.size();
727     if (len == 0) {
728         CLOGE("mediaInfoList len is invalid");
729         return result;
730     }
731     NAPI_CALL(env, napi_create_object(env, &result));
732     NAPI_CALL(env, napi_create_uint32(env, mediaInfoHolder.currentIndex, &value));
733     NAPI_CALL(env, napi_set_named_property(env, result, "currentIndex", value));
734     NAPI_CALL(env, napi_create_uint32(env, mediaInfoHolder.progressRefreshInterval, &value));
735     NAPI_CALL(env, napi_set_named_property(env, result, "progressRefreshInterval", value));
736     NAPI_CALL(env, napi_create_array_with_length(env, len, &value));
737     for (size_t i = 0; i < len; i++) {
738         napi_value mediaInfo = ConvertMediaInfoToJS(env, mediaInfoHolder.mediaInfoList[i]);
739         NAPI_CALL(env, napi_set_element(env, value, i, mediaInfo));
740     }
741     NAPI_CALL(env, napi_set_named_property(env, result, "mediaInfoList", value));
742     CLOGD("ConvertMediaInfoHolderToJS end");
743     return result;
744 }
745 
CallJSFunc(napi_env env,napi_ref func,size_t argc,napi_value argv[])746 void CallJSFunc(napi_env env, napi_ref func, size_t argc, napi_value argv[])
747 {
748     napi_value callback = nullptr;
749     napi_value undefined = nullptr;
750     napi_value callResult = nullptr;
751     if (napi_get_undefined(env, &undefined) != napi_ok) {
752         CLOGE("napi_get_undefined failed");
753         return;
754     }
755     if (napi_get_reference_value(env, func, &callback) != napi_ok) {
756         CLOGE("napi_get_reference_value failed");
757         return;
758     }
759     if (napi_call_function(env, undefined, callback, argc, argv, &callResult) != napi_ok) {
760         CLOGE("napi_call_function failed");
761     }
762 }
763 
GetJSFuncParams(napi_env env,napi_callback_info info,napi_value argv[],size_t expectedArgc,napi_valuetype expectedTypes[])764 bool GetJSFuncParams(napi_env env, napi_callback_info info, napi_value argv[], size_t expectedArgc,
765     napi_valuetype expectedTypes[])
766 {
767     napi_value thisVar = nullptr;
768     size_t argc = expectedArgc;
769     napi_status status = napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
770     if (status != napi_ok || argc != expectedArgc) {
771         CLOGE("napi_get_cb_info failed");
772         return false;
773     }
774 
775     for (size_t i = 0; i < expectedArgc; i++) {
776         napi_valuetype valueType = napi_undefined;
777         if (napi_typeof(env, argv[i], &valueType) != napi_ok) {
778             CLOGE("napi_typeof failed");
779             return false;
780         }
781         if (valueType != expectedTypes[i]) {
782             CLOGE("Wrong argument type. type:%d expected", expectedTypes[i]);
783             return false;
784         }
785     }
786 
787     return true;
788 }
789 
CheckJSParamsType(napi_env env,napi_value argv[],size_t expectedArgc,napi_valuetype expectedTypes[])790 bool CheckJSParamsType(napi_env env, napi_value argv[], size_t expectedArgc, napi_valuetype expectedTypes[])
791 {
792     for (size_t i = 0; i < expectedArgc; i++) {
793         napi_valuetype valueType = napi_undefined;
794         if (napi_typeof(env, argv[i], &valueType) != napi_ok) {
795             CLOGE("napi_typeof failed");
796             return false;
797         }
798         if (valueType != expectedTypes[i]) {
799             CLOGE("Wrong argument type. type:%d expected", expectedTypes[i]);
800             return false;
801         }
802     }
803 
804     return true;
805 }
806 } // namespace CastEngineClient
807 } // namespace CastEngine
808 } // namespace OHOS
809