• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# Working with Primitives Using JSVM-API
2
3## Introduction
4
5JSVM-API provides APIs for converting data between C/C++ and JavaScript (JS) data types and obtaining the JS object of the specified type.
6
7## Basic Concepts
8
9Before using JSVM-API to operate JS objects, you need to understand the following basic concepts:
10
11- Conversion between JS and C/C primitives: You can use JSVM-API to convert JS values to C/C++ data types, for example, convert a JS value into a C/C++ integer and convert a JS string into a C/C++ string array. You can also convert C/C++ data into a JS value and return the JS value to JS.
12
13## Available APIs
14
15| API                  | Description                                               |
16| ---------------------- | ------------------------------------------------------- |
17| OH_JSVM_CoerceToBool   | Converts a JS value to an object of the Boolean type.  |
18| OH_JSVM_CoerceToNumber | Converts a JS value to an object of the number type.   |
19| OH_JSVM_CoerceToObject | Converts a JS value to an object of the object type.   |
20| OH_JSVM_CoerceToString | Converts a JS value to an object of the string type.   |
21| OH_JSVM_GetBoolean       | Obtains a JS singleton object that is used to represent the given Boolean value. |
22| OH_JSVM_GetValueBool    | Obtains the C Boolean primitive equivalent of the given JS Boolean. |
23| OH_JSVM_GetGlobal      | Obtains the **global** object of the current environment.                                     |
24| OH_JSVM_GetNull          | Obtains the JS **null** object.                                       |
25| OH_JSVM_GetUndefined     | Obtains the JS **undefined** object.                                  |
26
27## Example
28
29If you are just starting out with JSVM-API, see [JSVM-API Development Process](use-jsvm-process.md). The following demonstrates only the C++ and ArkTS code involved in primitive-related APIs.
30
31### OH_JSVM_CoerceToBool
32
33Use **OH_JSVM_CoerceToBool** to forcibly convert a JS value to a JS Boolean value.
34
35CPP code:
36
37```cpp
38// hello.cpp
39#include "napi/native_api.h"
40#include "ark_runtime/jsvm.h"
41#include <hilog/log.h>
42// Register the CoerceToBool callback.
43static JSVM_CallbackStruct param[] = {
44    {.data = nullptr, .callback = CoerceToBool},
45};
46static JSVM_CallbackStruct *method = param;
47// Set a property descriptor named coerceToBool and associate it with a callback. This allows the CoerceToBool callback to be called from JS.
48static JSVM_PropertyDescriptor descriptor[] = {
49    {"coerceToBool", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
50};
51// Define OH_JSVM_CoerceToBool.
52static JSVM_Value CoerceToBool(JSVM_Env env, JSVM_CallbackInfo info)
53{
54    size_t argc = 1;
55    JSVM_Value args[1] = {nullptr};
56    OH_JSVM_GetCbInfo(env, info, &argc, args, nullptr, nullptr);
57    JSVM_Value boolean = nullptr;
58    JSVM_Status status = OH_JSVM_CoerceToBool(env, args[0], &boolean);
59    if (status != JSVM_OK) {
60        OH_LOG_ERROR(LOG_APP, "JSVM OH_JSVM_CoerceToBool failed");
61    } else {
62        bool result = false;
63        OH_JSVM_GetValueBool(env, boolean, &result);
64        OH_LOG_INFO(LOG_APP, "JSVM OH_JSVM_CoerceToBool success:%{public}d", result);
65    }
66    return boolean;
67}
68```
69
70ArkTS code:
71
72```ts
73import hilog from "@ohos.hilog"
74// Import the native APIs.
75import napitest from "libentry.so"
76let script: string = `coerceToBool("123")`;
77try {
78  let result = napitest.runJsVm(script);
79  hilog.info(0x0000, 'JSVM', 'CoerceToBool: %{public}s', result);
80} catch (error) {
81  hilog.error(0x0000, 'JSVM', 'CoerceToBool: %{public}s', error.message);
82}
83```
84
85### OH_JSVM_CoerceToNumber
86
87Use **OH_JSVM_CoerceToNumber** to forcibly convert a JS value to a JS number.
88
89CPP code:
90
91```cpp
92// hello.cpp
93#include "napi/native_api.h"
94#include "ark_runtime/jsvm.h"
95#include <hilog/log.h>
96// Register the CoerceToNumber callback.
97static JSVM_CallbackStruct param[] = {
98    {.data = nullptr, .callback = CoerceToNumber},
99};
100static JSVM_CallbackStruct *method = param;
101// Set a property descriptor named coerceToNumber and associate it with a callback. This allows the CoerceToNumber callback to be called from JS.
102static JSVM_PropertyDescriptor descriptor[] = {
103    {"coerceToNumber", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
104};
105// Define OH_JSVM_CoerceToNumber.
106static JSVM_Value CoerceToNumber(JSVM_Env env, JSVM_CallbackInfo info)
107{
108    size_t argc = 1;
109    JSVM_Value args[1] = {nullptr};
110    OH_JSVM_GetCbInfo(env, info, &argc, args, nullptr, nullptr);
111    JSVM_Value number = nullptr;
112    JSVM_Status status = OH_JSVM_CoerceToNumber(env, args[0], &number);
113    if (status != JSVM_OK) {
114        OH_LOG_ERROR(LOG_APP, "JSVM OH_JSVM_CoerceToNumber failed");
115    } else {
116        int32_t result = 0;
117        OH_JSVM_GetValueInt32(env, number, &result);
118        OH_LOG_INFO(LOG_APP, "JSVM OH_JSVM_CoerceToNumber success:%{public}d", result);
119    }
120    return number;
121}
122```
123
124ArkTS code:
125
126```ts
127import hilog from "@ohos.hilog"
128// Import the native APIs.
129import napitest from "libentry.so"
130let script: string = `coerceToNumber(true)`;
131try {
132  let result = napitest.runJsVm(script);
133  hilog.info(0x0000, 'JSVM', 'CoerceToNumber: %{public}s', result);
134} catch (error) {
135  hilog.error(0x0000, 'JSVM', 'CoerceToNumber: %{public}s', error.message);
136}
137```
138
139### OH_JSVM_CoerceToObject
140
141Use **OH_JSVM_CoerceToObject** to forcibly convert a JS value to a JS object.
142
143CPP code:
144
145```cpp
146// hello.cpp
147#include "napi/native_api.h"
148#include "ark_runtime/jsvm.h"
149#include <hilog/log.h>
150// Register the CoerceToObjec callback.
151static JSVM_CallbackStruct param[] = {
152    {.data = nullptr, .callback = CoerceToObject},
153};
154static JSVM_CallbackStruct *method = param;
155// Set a property descriptor named coerceToObject and associate it with a callback. This allows the CoerceToObject callback to be called from JS.
156static JSVM_PropertyDescriptor descriptor[] = {
157    {"coerceToObject", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
158};
159// Define OH_JSVM_CoerceToObject.
160static JSVM_Value CoerceToObject(JSVM_Env env, JSVM_CallbackInfo info)
161{
162    size_t argc = 1;
163    JSVM_Value args[1] = {nullptr};
164    OH_JSVM_GetCbInfo(env, info, &argc, args, nullptr, nullptr);
165    JSVM_Value obj;
166    JSVM_Status status = OH_JSVM_CoerceToObject(env, args[0], &obj);
167    if (status != JSVM_OK) {
168        OH_JSVM_ThrowError(env, nullptr, "JSVM OH_JSVM_CoerceToObject failed");
169        return nullptr;
170    } else {
171        OH_LOG_INFO(LOG_APP, "JSVM OH_JSVM_CoerceToObject success");
172    }
173    return obj;
174}
175```
176
177ArkTS code:
178
179```ts
180import hilog from "@ohos.hilog"
181// Import the native APIs.
182import napitest from "libentry.so"
183let script: string = `coerceToObject(123)`;
184try {
185  let result = napitest.runJsVm(script);
186  hilog.info(0x0000, 'JSVM', 'CoerceToObject001: %{public}s', result);
187} catch (error) {
188  hilog.error(0x0000, 'JSVM', 'CoerceToObject001: %{public}s', error.message);
189}
190```
191
192### OH_JSVM_CoerceToString
193
194Use **OH_JSVM_CoerceToString** to forcibly convert a JS value to a JS string.
195
196CPP code:
197
198```cpp
199// hello.cpp
200#include "napi/native_api.h"
201#include "ark_runtime/jsvm.h"
202#include <hilog/log.h>
203// Register the CoerceToString callback.
204static JSVM_CallbackStruct param[] = {
205    {.data = nullptr, .callback = CoerceToString},
206};
207static JSVM_CallbackStruct *method = param;
208// Set a property descriptor named coerceToString and associate it with a callback. This allows the CoerceToString callback to be called from JS.
209static JSVM_PropertyDescriptor descriptor[] = {
210    {"coerceToString", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
211};
212// Define OH_JSVM_CoerceToString.
213static JSVM_Value CoerceToString(JSVM_Env env, JSVM_CallbackInfo info)
214{
215    size_t argc = 1;
216    JSVM_Value args[1] = {nullptr};
217    OH_JSVM_GetCbInfo(env, info, &argc, args, nullptr, nullptr);
218    JSVM_Value str;
219    JSVM_Status status = OH_JSVM_CoerceToString(env, args[0], &str);
220    if (status != JSVM_OK) {
221        OH_JSVM_ThrowError(env, nullptr, "JSVM OH_JSVM_CoerceToString fail");
222        return nullptr;
223    } else {
224        OH_LOG_INFO(LOG_APP, "JSVM OH_JSVM_CoerceToString success");
225    }
226    return str;
227}
228```
229
230ArkTS code:
231
232```ts
233import hilog from "@ohos.hilog"
234// Import the native APIs.
235import napitest from "libentry.so"
236let script: string = `coerceToString(22222)`;
237try {
238  let result = napitest.runJsVm(script);
239  hilog.info(0x0000, 'JSVM', 'CoerceToString: %{public}s', result);
240} catch (error) {
241  hilog.error(0x0000, 'JSVM', 'CoerceToString: %{public}s', error.message);
242}
243```
244
245### OH_JSVM_GetBoolean
246
247Use **OH_JSVM_GetBoolean** to obtain a JS singleton object that is used to represent the given Boolean value.
248
249CPP code:
250
251```cpp
252// hello.cpp
253#include "napi/native_api.h"
254#include "ark_runtime/jsvm.h"
255#include <hilog/log.h>
256// Register the GetBoolean callback.
257static JSVM_CallbackStruct param[] = {
258    {.data = nullptr, .callback = GetBoolean},
259};
260static JSVM_CallbackStruct *method = param;
261// Set a property descriptor named getBoolean and associate it with a callback. This allows the GetBoolean callback to be called from JS.
262static JSVM_PropertyDescriptor descriptor[] = {
263    {"getBoolean", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
264};
265// Define OH_JSVM_GetBoolean.
266static JSVM_Value GetBoolean(JSVM_Env env, JSVM_CallbackInfo info)
267{
268    // Pass in two parameters and parse them.
269    size_t argc = 2;
270    JSVM_Value argv[2] = {nullptr};
271    OH_JSVM_GetCbInfo(env, info, &argc, argv, nullptr, nullptr);
272    int32_t paramData;
273    OH_JSVM_GetValueInt32(env, argv[0], &paramData);
274    int32_t paramValue;
275    OH_JSVM_GetValueInt32(env, argv[1], &paramValue);
276    JSVM_Value returnValue = nullptr;
277    bool type = false;
278    if (paramData == paramValue)
279         {
280            OH_LOG_INFO(LOG_APP, "JSVM resultType equal");
281            type = true;
282        }
283    JSVM_Status status = OH_JSVM_GetBoolean(env, type, &returnValue);
284    if (status != JSVM_OK) {
285        OH_LOG_ERROR(LOG_APP, "JSVM OH_JSVM_CoerceToNumber fail");
286    } else {
287        bool result = false;
288        OH_JSVM_GetValueBool(env, returnValue, &result);
289        OH_LOG_INFO(LOG_APP, "JSVM OH_JSVM_CoerceToNumber success:%{public}d", result);
290    }
291    // Return the result.
292    return returnValue;
293}
294```
295
296ArkTS code:
297
298```ts
299import hilog from "@ohos.hilog"
300// Import the native APIs.
301import napitest from "libentry.so"
302try {
303  let data = 1;
304  let compareData = 2;
305  let script: string = `getBoolean(${data}, ${compareData})`;
306  let result = napitest.runJsVm(script);
307  hilog.info(0x0000, 'JSVM', 'GetBoolean: %{public}s', result);
308} catch (error) {
309  hilog.error(0x0000, 'JSVM', 'GetBoolean: %{public}s', error.message);
310}
311try {
312  let data = 1;
313  let compareData = 1;
314  let script: string = `getBoolean(${data}, ${compareData})`;
315  let result = napitest.runJsVm(script);
316  hilog.info(0x0000, 'JSVM', 'GetBoolean: %{public}s', result);
317} catch (error) {
318  hilog.error(0x0000, 'JSVM', 'GetBoolean: %{public}s', error.message);
319}
320```
321
322### OH_JSVM_GetValueBool
323
324Use **OH_JSVM_GetValueBool** to obtain the C Boolean equivalent of the given JS Boolean.
325
326CPP code:
327
328```cpp
329// hello.cpp
330#include "napi/native_api.h"
331#include "ark_runtime/jsvm.h"
332#include <hilog/log.h>
333// Register the GetValueBool callback.
334static JSVM_CallbackStruct param[] = {
335    {.data = nullptr, .callback = GetValueBool},
336};
337static JSVM_CallbackStruct *method = param;
338// Set a property descriptor named getValueBool and associate it with a callback. This allows the GetValueBool callback to be called from JS.
339static JSVM_PropertyDescriptor descriptor[] = {
340    {"getValueBool", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
341};
342// Define OH_JSVM_GetValueBool.
343static JSVM_Value GetValueBool(JSVM_Env env, JSVM_CallbackInfo info)
344{
345    size_t argc = 1;
346    JSVM_Value args[1] = {nullptr};
347    OH_JSVM_GetCbInfo(env, info, &argc, args, nullptr, nullptr);
348    bool result;
349    JSVM_Status status = OH_JSVM_GetValueBool(env, args[0], &result);
350    if (status == JSVM_BOOLEAN_EXPECTED || status != JSVM_OK) {
351        // If OH_JSVM_GetValueBool is successful, JSVM_OK is returned. If a non-Boolean value is passed in, JSVM_BOOLEAN_EXPECTED is returned.
352        OH_LOG_ERROR(LOG_APP, "JSVM OH_JSVM_GetValueBool fail:%{public}d", status);
353        return nullptr;
354    } else {
355        OH_LOG_INFO(LOG_APP, "JSVM OH_JSVM_GetValueBool success:%{public}d", result);
356    }
357    JSVM_Value boolJv;
358    OH_JSVM_GetBoolean(env, result, &boolJv);
359    return boolJv;
360}
361```
362
363ArkTS code:
364
365```ts
366import hilog from "@ohos.hilog"
367// Import the native APIs.
368import napitest from "libentry.so"
369// Pass in a Boolean value and a non-Boolean value. After the Boolean value is passed in, the Boolean value is returned. After the non-Boolean value is passed in, undefined is returned.
370try {
371  let data = `"abc"`;
372  let script: string = `getValueBool(${data})`;
373  let result = napitest.runJsVm(script);
374  hilog.info(0x0000, 'JSVM', 'GetValueBool: %{public}s', result);
375} catch (error) {
376  hilog.error(0x0000, 'JSVM', 'GetValueBool: %{public}s', error.message);
377}
378try {
379  let data = true;
380  let script: string = `getValueBool(${data})`;
381  let result = napitest.runJsVm(script);
382  hilog.info(0x0000, 'JSVM', 'GetValueBool: %{public}s', result);
383} catch (error) {
384  hilog.error(0x0000, 'JSVM', 'GetValueBool: %{public}s', error.message);
385}
386try {
387  let data = false;
388  let script: string = `getValueBool(${data})`;
389  let result = napitest.runJsVm(script);
390  hilog.info(0x0000, 'JSVM', 'GetValueBool: %{public}s', result);
391} catch (error) {
392  hilog.error(0x0000, 'JSVM', 'GetValueBool: %{public}s', error.message);
393}
394```
395
396### OH_JSVM_GetGlobal
397
398Use **OH_JSVM_GetGlobal** to obtain a JS global object. You can use this API to obtain the **JSVM_Value** that represents a JS global object, so that the JSVM module can interact with the global variables and functions defined in the JS context.
399
400CPP code:
401
402```cpp
403// hello.cpp
404#include "napi/native_api.h"
405#include "ark_runtime/jsvm.h"
406#include <hilog/log.h>
407// Register the GetGlobal callback.
408static JSVM_CallbackStruct param[] = {
409    {.data = nullptr, .callback = GetGlobal},
410};
411static JSVM_CallbackStruct *method = param;
412// Set a property descriptor named getGlobal and associate it with a callback. This allows the GetGlobal callback to be called from JS.
413static JSVM_PropertyDescriptor descriptor[] = {
414    {"getGlobal", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
415};
416// Define OH_JSVM_GetGlobal.
417static JSVM_Value GetGlobal(JSVM_Env env, JSVM_CallbackInfo info)
418{
419    // Obtain the global object.
420    JSVM_Value value = nullptr;
421    JSVM_Value global;
422    OH_JSVM_CreateInt32(env, 1, &value);
423    JSVM_Status status = OH_JSVM_GetGlobal(env, &global);
424    OH_JSVM_SetNamedProperty(env, global, "Row", value);
425    if (status != JSVM_OK) {
426        OH_LOG_ERROR(LOG_APP, "JSVM OH_JSVM_GetGlobal fail");
427    } else {
428        OH_LOG_INFO(LOG_APP, "JSVM OH_JSVM_GetGlobal success");
429    }
430    return global;
431}
432```
433
434ArkTS code:
435
436```ts
437import hilog from "@ohos.hilog"
438// Import the native APIs.
439import napitest from "libentry.so"
440let script: string = `getGlobal()`
441try {
442  let result = napitest.runJsVm(script);
443  hilog.info(0x0000, 'JSVM', 'GetGlobal: %{public}s', result);
444} catch (error) {
445  hilog.error(0x0000, 'JSVM', 'GetGlobal: %{public}s', error.message);
446}
447```
448
449### OH_JSVM_GetNull
450
451Use **OH_JSVM_GetNull** to obtain a JS **null** object.
452
453CPP code:
454
455```cpp
456// hello.cpp
457#include "napi/native_api.h"
458#include "ark_runtime/jsvm.h"
459#include <hilog/log.h>
460// Register the GetNull callback.
461static JSVM_CallbackStruct param[] = {
462    {.data = nullptr, .callback = GetNull},
463};
464static JSVM_CallbackStruct *method = param;
465// Set a property descriptor named getNull and associate it with a callback. This allows the GetNull callback to be called from JS.
466static JSVM_PropertyDescriptor descriptor[] = {
467    {"getNull", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
468};
469// Define OH_JSVM_GetNull.
470static JSVM_Value GetNull(JSVM_Env env, JSVM_CallbackInfo info) {
471    JSVM_Value nullValue;
472    JSVM_Status status = OH_JSVM_GetNull(env, &nullValue);
473    if (status != JSVM_OK) {
474        OH_LOG_ERROR(LOG_APP, "JSVM OH_JSVM_GetNull fail");
475    } else {
476        OH_LOG_INFO(LOG_APP, "JSVM OH_JSVM_GetNull success");
477    }
478    return nullValue;
479}
480```
481
482ArkTS code:
483
484```ts
485import hilog from "@ohos.hilog"
486// Import the native APIs.
487import napitest from "libentry.so"
488try {
489  let script: string = `getNull()`;
490  let result = napitest.runJsVm(script);
491  hilog.info(0x0000, 'JSVM', 'GetNull: %{public}s', result);
492} catch (error) {
493  hilog.error(0x0000, 'JSVM', 'GetNull: %{public}s', error.message);
494}
495```
496
497### OH_JSVM_GetUndefined
498
499Use **OH_JSVM_GetUndefined** to obtain a JS **undefined** object.
500
501CPP code:
502
503```cpp
504// hello.cpp
505#include "napi/native_api.h"
506#include "ark_runtime/jsvm.h"
507#include <hilog/log.h>
508// Register the GetUndefined callback.
509static JSVM_CallbackStruct param[] = {
510    {.data = nullptr, .callback = GetUndefined},
511};
512static JSVM_CallbackStruct *method = param;
513// Set a property descriptor named getUndefined and associate it with a callback. This allows the GetUndefined callback to be called from JS.
514static JSVM_PropertyDescriptor descriptor[] = {
515    {"getUndefined", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
516};
517// Define OH_JSVM_GetUndefined.
518static JSVM_Value GetUndefined(JSVM_Env env, JSVM_CallbackInfo info)
519{
520    // Obtain and parse the parameters passed in.
521    size_t argc = 1;
522    JSVM_Value args[1] = {nullptr};
523    OH_JSVM_GetCbInfo(env, info, &argc, args, nullptr, nullptr);
524    // Create the value 'undefined'.
525    JSVM_Value value;
526    JSVM_Status status = OH_JSVM_GetUndefined(env, &value);
527    if (status != JSVM_OK) {
528        OH_LOG_ERROR(LOG_APP, "JSVM OH_JSVM_GetUndefined failed");
529    } else {
530        OH_LOG_INFO(LOG_APP, "JSVM OH_JSVM_GetUndefined success");
531    }
532    return value;
533}
534```
535
536API declaration:
537
538ArkTS code:
539
540```ts
541import hilog from "@ohos.hilog"
542// Import the native APIs.
543import napitest from "libentry.so"
544try {
545  let script: string = `getUndefined()`;
546  let result = napitest.runJsVm(script);
547  hilog.info(0x0000, 'JSVM', 'GetUndefined: %{public}s', result);
548} catch (error) {
549  hilog.error(0x0000, 'JSVM', 'GetUndefined: %{public}s', error.message);
550}
551```
552