• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# Working with Objects Using JSVM-API
2
3## Overview
4
5JSVM-API provides APIs for basic JavaScript (JS) object operations, including creating an object, obtaining the prototype of an object, freezing or sealing an object, and checking the object type. You can use these APIs to manage JS objects.
6
7## Basic Concepts
8
9You may need to define and operate objects when using JSVM-API in development. For example, define an API with an object as an input parameter, perform operations on the object, and have a result object returned. In this process, you need to ensure that the API definition is clear and compatible with the properties and methods of the object.
10
11- API: defines the interaction protocol between components. An API includes input parameters, output result, and possible error handling. By calling APIs, components can interact and exchange data with each other without knowing the internal implementation details.
12- Object: a composite data type that allows values of different types to be stored as an independent entity in JS. An object is a collection of properties and methods. A property is a value associated with an object, and a method is an operation that the object can perform.
13
14## Available APIs
15
16| API                      | Description                                    |
17| -------------------------- | -------------------------------------------- |
18| OH_JSVM_GetPrototype         | Obtains the prototype of a JS object.            |
19| OH_JSVM_CreateObject         | Creates a default JS object.                  |
20| OH_JSVM_ObjectFreeze         | Freezes a JS object. Once a JS object is frozen, new properties cannot be added to it, existing properties cannot be removed, the enumerability, configurability, or writability of existing properties cannot be changed, and the values of existing properties cannot be changed.                            |
21| OH_JSVM_ObjectSeal           |  Seals a JS object. Once a JS object is sealed, new properties cannot be added to it and all existing properties are marked as unconfigurable.                            |
22| OH_JSVM_Typeof                | Returns the type of a JS object. |
23| OH_JSVM_Instanceof            | Checks whether an object is an instance of a constructor.   |
24| OH_JSVM_TypeTagObject       | Associates the value of the **type_tag** pointer with a JS object or an external object.                 |
25| OH_JSVM_CheckObjectTypeTag | Checks whether a tag matches the tag type of an object. |
26| OH_JSVM_CreateSymbol         | Creates a symbol object based on the given descriptor.                    |
27|OH_JSVM_SymbolFor | Searches for a symbol with the given key in a global (runtime-wide) symbol registry. If a match is found, the symbol will be returned. Otherwise, a symbol will be created in the registry. |
28| OH_JSVM_CreateExternal       | Creates a JS object that wraps an external pointer.              |
29| OH_JSVM_GetValueExternal    | Obtains the external data pointer previously passed to **OH_JSVM_CreateExternal**.                 |
30
31## Example
32
33If you are just starting out with JSVM-API, see [JSVM-API Development Process](use-jsvm-process.md). The following only demonstrates the C++ and ArkTS code for object management APIs.
34
35### OH_JSVM_GetPrototype
36
37Obtains the prototype of a JS object.
38
39CPP code:
40
41```cpp
42// hello.cpp
43#include "napi/native_api.h"
44#include "ark_runtime/jsvm.h"
45#include <hilog/log.h>
46// Register the GetPrototype callback.
47static JSVM_CallbackStruct param[] = {
48    {.data = nullptr, .callback = GetPrototype},
49};
50static JSVM_CallbackStruct *method = param;
51// Set a property descriptor named getPrototype and associate it with a callback. This allows the GetPrototype callback to be called from JS.
52static JSVM_PropertyDescriptor descriptor[] = {
53    {"getPrototype", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
54};
55// Define OH_JSVM_GetPrototype.
56static JSVM_Value GetPrototype(JSVM_Env env, JSVM_CallbackInfo info)
57{
58    // Create an empty object.
59    JSVM_Value obj = nullptr;
60    OH_JSVM_CreateObject(env, &obj);
61    const char *testNameStr = "set and get proto";
62    JSVM_Value propValue = nullptr;
63    JSVM_Value key = nullptr;
64    OH_JSVM_CreateStringUtf8(env, "name", JSVM_AUTO_LENGTH, &key);
65    OH_JSVM_CreateStringUtf8(env, testNameStr, strlen(testNameStr), &propValue);
66    OH_JSVM_SetProperty(env, obj, key, propValue);
67    // Obtain properties.
68    JSVM_Value propResult = nullptr;
69    JSVM_Status status = OH_JSVM_GetProperty(env, obj, key, &propResult);
70    if (status != JSVM_OK) {
71        OH_LOG_ERROR(LOG_APP, "JSVM GetPrototype fail");
72    } else {
73        OH_LOG_INFO(LOG_APP, "JSVM GetPrototype success");
74    }
75    return propResult;
76}
77```
78
79ArkTS code:
80
81```ts
82import hilog from "@ohos.hilog"
83// Import the native APIs.
84import napitest from "libentry.so"
85let script: string = `getPrototype()`;
86try {
87  let result = napitest.runJsVm(script);
88  hilog.info(0x0000, 'testJSVM', 'Test JSVM getPrototype: %{public}s', result);
89} catch (error) {
90  hilog.error(0x0000, 'testJSVM', 'Test JSVM getPrototype error: %{public}s', error.message);
91}
92```
93
94### OH_JSVM_CreateObject
95
96Creates a default JS object.
97
98CPP code:
99
100```cpp
101// hello.cpp
102#include "napi/native_api.h"
103#include "ark_runtime/jsvm.h"
104#include <hilog/log.h>
105// Register the CreateObject callback.
106static JSVM_CallbackStruct param[] = {
107    {.data = nullptr, .callback = CreateObject},
108};
109static JSVM_CallbackStruct *method = param;
110// Set a property descriptor named createObject and associate it with a callback. This allows the CreateObject callback to be called from JS.
111static JSVM_PropertyDescriptor descriptor[] = {
112    {"createObject", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
113};
114// Define OH_JSVM_CreateObject.
115static JSVM_Value CreateObject(JSVM_Env env, JSVM_CallbackInfo info)
116{
117    JSVM_Value object = nullptr;
118    // Create an empty object.
119    JSVM_Status status = OH_JSVM_CreateObject(env, &object);
120    if (status != JSVM_OK) {
121        OH_LOG_ERROR(LOG_APP, "JSVM CreateObject fail");
122    } else {
123        OH_LOG_INFO(LOG_APP, "JSVM CreateObject success");
124    }
125    // Set the object property.
126    JSVM_Value name = nullptr;
127    // Set the property name to "name".
128    OH_JSVM_CreateStringUtf8(env, "name", JSVM_AUTO_LENGTH, &name);
129    JSVM_Value value = nullptr;
130    // Set the property value to "Hello from N-API!"
131    OH_JSVM_CreateStringUtf8(env, "Hello OH_JSVM_CreateObject!", JSVM_AUTO_LENGTH, &value);
132    // Set the property on the object.
133    OH_JSVM_SetProperty(env, object, name, value);
134    return object;
135}
136```
137
138ArkTS code:
139
140```ts
141import hilog from "@ohos.hilog"
142// Import the native APIs.
143import napitest from "libentry.so"
144let script: string = `createObject()`;
145try {
146  let result = napitest.runJsVm(script);
147  hilog.info(0x0000, 'testJSVM', 'Test JSVM createObject: %{public}s', result);
148} catch (error) {
149  hilog.error(0x0000, 'testJSVM', 'Test JSVM createObject error: %{public}s', error.message);
150}
151```
152
153### OH_JSVM_ObjectFreeze
154
155Freezes a JS object. Once a JS object is frozen, new properties cannot be added to it, existing properties cannot be removed, the enumerability, configurability, or writability of existing properties cannot be changed, and the values of existing properties cannot be changed.
156
157CPP code:
158
159```cpp
160// hello.cpp
161#include "napi/native_api.h"
162#include "ark_runtime/jsvm.h"
163#include <hilog/log.h>
164// Register the ObjectFreeze callback.
165static JSVM_CallbackStruct param[] = {
166    {.data = nullptr, .callback = ObjectFreeze},
167};
168static JSVM_CallbackStruct *method = param;
169// Set a property descriptor named objectFreeze and associate it with a callback. This allows the ObjectFreeze callback to be called from JS.
170static JSVM_PropertyDescriptor descriptor[] = {
171    {"objectFreeze", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
172};
173// Define OH_JSVM_ObjectFreeze.
174static JSVM_Value ObjectFreeze(JSVM_Env env, JSVM_CallbackInfo info)
175{
176    // Accept an object passed in from JS.
177    size_t argc = 1;
178    JSVM_Value argv[1] = {nullptr};
179    OH_JSVM_GetCbInfo(env, info, &argc, argv, nullptr, nullptr);
180    // Call OH_JSVM_ObjectFreeze to freeze the object passed in.
181    JSVM_Status status = OH_JSVM_ObjectFreeze(env, argv[0]);
182    if (status == JSVM_OK) {
183        OH_LOG_INFO(LOG_APP, "Test JSVM OH_JSVM_ObjectFreeze success");
184    }
185    // Check whether the properties of the frozen object can be modified.
186    JSVM_Value value = nullptr;
187    OH_JSVM_CreateInt32(env, 111111, &value);
188    OH_JSVM_SetNamedProperty(env, argv[0], "data", value);
189    // Return the properties modified after the freezing to JS.
190    return argv[0];
191}
192```
193
194ArkTS code:
195
196```ts
197import hilog from "@ohos.hilog"
198// Import the native APIs.
199import napitest from "libentry.so"
200let script: string = `
201  let obj = { data: 55, message: "hello world"};
202  objectFreeze(obj)
203`
204try {
205  let result = napitest.runJsVm(script);
206  // The property values of the frozen object remain unchanged.
207  hilog.info(0x0000, 'testJSVM', 'Test JSVM objectFreeze: %{public}s', result);
208} catch (error) {
209  hilog.error(0x0000, 'testJSVM', 'Test JSVM objectFreeze error: %{public}s', error.message);
210}
211```
212
213### OH_JSVM_ObjectSeal
214
215Seals a JS object. Once a JS object is sealed, new properties cannot be added to it and all existing properties are marked as unconfigurable.
216
217CPP code:
218
219```cpp
220// hello.cpp
221#include "napi/native_api.h"
222#include "ark_runtime/jsvm.h"
223#include <hilog/log.h>
224// Register the ObjectSeal callback.
225static JSVM_CallbackStruct param[] = {
226    {.data = nullptr, .callback = ObjectSeal},
227};
228static JSVM_CallbackStruct *method = param;
229// Set a property descriptor named objectSeal and associate it with a callback. This allows the ObjectSeal callback to be called from JS.
230static JSVM_PropertyDescriptor descriptor[] = {
231    {"objectSeal", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
232};
233// Define OH_JSVM_ObjectSeal.
234static JSVM_Value ObjectSeal(JSVM_Env env, JSVM_CallbackInfo info)
235{
236    // Accept an object passed in from JS.
237    size_t argc = 1;
238    JSVM_Value argv[1] = {nullptr};
239    OH_JSVM_GetCbInfo(env, info, &argc, argv, nullptr, nullptr);
240    // Call OH_JSVM_ObjectSeal to seal the object passed in.
241    JSVM_Status status = OH_JSVM_ObjectSeal(env, argv[0]);
242    if (status == JSVM_OK) {
243        OH_LOG_INFO(LOG_APP, "Test JSVM OH_JSVM_ObjectSeal success");
244    }
245    // Check whether the properties of the sealed object can be modified, deleted, or added.
246    // Modify a property of the sealed object.
247    JSVM_Value changeValue = nullptr;
248    OH_JSVM_CreateInt32(env, 111111, &changeValue);
249    OH_JSVM_SetNamedProperty(env, argv[0], "data", changeValue);
250    // Delete a property from the sealed object.
251    JSVM_Value deleteProperty = nullptr;
252    OH_JSVM_CreateStringUtf8(env, "message", JSVM_AUTO_LENGTH, &deleteProperty);
253    bool result = false;
254    OH_JSVM_DeleteProperty(env, argv[0], deleteProperty, &result);
255    if (result) {
256        OH_LOG_INFO(LOG_APP, "Test JSVM OH_JSVM_ObjectSeal failed");
257    }
258    // Add a property to the sealed object.
259    JSVM_Value addValue = nullptr;
260    OH_JSVM_CreateStringUtf8(env, "addValue", JSVM_AUTO_LENGTH, &addValue);
261    OH_JSVM_SetNamedProperty(env, argv[0], "newProperty", addValue);
262    // Return the modified object to JS.
263    return argv[0];
264}
265```
266
267ArkTS code:
268
269```ts
270import hilog from "@ohos.hilog"
271// Import the native APIs.
272import napitest from "libentry.so"
273let script: string = `
274  let obj = { data: 55, message: "hello world"};
275  objectSeal(obj)
276`
277try {
278  let result = napitest.runJsVm(script);
279  // Properties of a sealed object can be modified, but cannot be added or deleted.
280  hilog.info(0x0000, 'testJSVM', 'Test JSVM objectSeal: %{public}s', result);
281} catch (error) {
282  hilog.error(0x0000, 'testJSVM', 'Test JSVM objectSeal error: %{public}s', error.message);
283}
284```
285
286### OH_JSVM_Typeof
287
288Returns the type of a JS object.
289
290CPP code:
291
292```cpp
293// hello.cpp
294#include "napi/native_api.h"
295#include "ark_runtime/jsvm.h"
296#include <hilog/log.h>
297// Register the GetTypeof callback.
298static JSVM_CallbackStruct param[] = {
299    {.data = nullptr, .callback = GetTypeof},
300};
301static JSVM_CallbackStruct *method = param;
302// Set a property descriptor named getTypeof and associate it with a callback. This allows the GetTypeof callback to be called from JS.
303static JSVM_PropertyDescriptor descriptor[] = {
304    {"getTypeof", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
305};
306// Define OH_JSVM_Typeof.
307static JSVM_Value GetTypeof(JSVM_Env env, JSVM_CallbackInfo info) {
308    size_t argc = 1;
309    JSVM_Value args[1] = {nullptr};
310    OH_JSVM_GetCbInfo(env, info, &argc, args, nullptr, nullptr);
311    JSVM_ValueType valueType;
312    OH_JSVM_Typeof(env, args[0], &valueType);
313    JSVM_Value type = nullptr;
314    switch (valueType) {
315    case JSVM_UNDEFINED:
316        OH_LOG_INFO(LOG_APP, "JSVM Input type is undefined");
317        OH_JSVM_CreateStringUtf8(env, "Input type is undefined", JSVM_AUTO_LENGTH, &type);
318        break;
319    case JSVM_NULL:
320        OH_LOG_INFO(LOG_APP, "JSVM Input type is null");
321        OH_JSVM_CreateStringUtf8(env, "Input type is null", JSVM_AUTO_LENGTH, &type);
322        break;
323    case JSVM_BOOLEAN:
324        OH_LOG_INFO(LOG_APP, "JSVM Input type is boolean");
325        OH_JSVM_CreateStringUtf8(env, "Input type is boolean", JSVM_AUTO_LENGTH, &type);
326        break;
327    case JSVM_NUMBER:
328        OH_LOG_INFO(LOG_APP, "JSVM Input type is number");
329        OH_JSVM_CreateStringUtf8(env, "Input type is number", JSVM_AUTO_LENGTH, &type);
330        break;
331    case JSVM_STRING:
332        OH_LOG_INFO(LOG_APP, "JSVM Input type is string");
333        OH_JSVM_CreateStringUtf8(env, "Input type is string", JSVM_AUTO_LENGTH, &type);
334        break;
335    case JSVM_SYMBOL:
336        OH_LOG_INFO(LOG_APP, "JSVM Input type is symbol");
337        OH_JSVM_CreateStringUtf8(env, "Input type is symbol", JSVM_AUTO_LENGTH, &type);
338        break;
339    case JSVM_OBJECT:
340        OH_LOG_INFO(LOG_APP, "JSVM Input type is object");
341        OH_JSVM_CreateStringUtf8(env, "Input type is object", JSVM_AUTO_LENGTH, &type);
342        break;
343    case JSVM_FUNCTION:
344        OH_LOG_INFO(LOG_APP, "JSVM Input type is function");
345        OH_JSVM_CreateStringUtf8(env, "Input type is function", JSVM_AUTO_LENGTH, &type);
346        break;
347    case JSVM_EXTERNAL:
348        OH_LOG_INFO(LOG_APP, "JSVM Input type is external");
349        OH_JSVM_CreateStringUtf8(env, "Input type is external", JSVM_AUTO_LENGTH, &type);
350        break;
351    case JSVM_BIGINT:
352        OH_LOG_INFO(LOG_APP, "JSVM Input type is bigint");
353        OH_JSVM_CreateStringUtf8(env, "Input type is bigint", JSVM_AUTO_LENGTH, &type);
354        break;
355    default:
356        OH_LOG_INFO(LOG_APP, "JSVM Input type does not match any");
357        OH_JSVM_CreateStringUtf8(env, " ", JSVM_AUTO_LENGTH, &type);
358        break;
359    }
360    return type;
361}
362```
363
364ArkTS code:
365
366```ts
367import hilog from "@ohos.hilog"
368// Import the native APIs.
369import napitest from "libentry.so"
370let script: string = `
371getTypeof(true);
372  `;
373try {
374  let result = napitest.runJsVm(script);
375  hilog.info(0x0000, 'JSVM', 'GetTypeof: %{public}s', result);
376} catch (error) {
377  hilog.error(0x0000, 'JSVM', 'GetTypeof: %{public}s', error.message);
378}
379```
380
381### OH_JSVM_Instanceof
382
383Checks whether an object is an instance of a constructor.
384
385CPP code:
386
387```cpp
388// hello.cpp
389#include "napi/native_api.h"
390#include "ark_runtime/jsvm.h"
391#include <hilog/log.h>
392// Register the InstanceOf callback.
393static JSVM_CallbackStruct param[] = {
394    {.data = nullptr, .callback = InstanceOf},
395};
396static JSVM_CallbackStruct *method = param;
397// Set a property descriptor named instanceOf and associate it with a callback. This allows the InstanceOf callback to be called from JS.
398static JSVM_PropertyDescriptor descriptor[] = {
399    {"instanceOf", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
400};
401// Define OH_JSVM_Instanceof.
402static JSVM_Value InstanceOf(JSVM_Env env, JSVM_CallbackInfo info)
403{
404    // Obtain the two parameters passed from JS.
405    size_t argc = 2;
406    JSVM_Value args[2] = {nullptr};
407    OH_JSVM_GetCbInfo(env, info, &argc, args, nullptr, nullptr);
408    bool result = false;
409    JSVM_Status status = OH_JSVM_Instanceof(env, args[0], args[1], &result);
410    if (status != JSVM_OK) {
411        OH_LOG_ERROR(LOG_APP, "JSVM InstanceOf fail");
412    } else {
413        OH_LOG_INFO(LOG_APP, "JSVM InstanceOf: %{public}d", result);
414    }
415    JSVM_Value returnValue = nullptr;
416    OH_JSVM_GetBoolean(env, result, &returnValue);
417    return returnValue;
418}
419```
420
421ArkTS code:
422
423```ts
424import hilog from "@ohos.hilog"
425// Import the native APIs.
426import napitest from "libentry.so"
427let script: string = `
428      class Person {
429        name;
430        age;
431        constructor(name, age) {
432          this.name = name;
433          this.age = age;
434        }
435      }
436     instanceOf(new Person('Alice', 30), Person);
437     ;
438        `;
439try {
440  let result = napitest.runJsVm(script.toString());
441  hilog.info(0x0000, 'JSVM', 'InstanceOf: %{public}s', result);
442} catch (error) {
443  hilog.error(0x0000, 'JSVM', 'InstanceOf: %{public}s', error.message);
444}
445```
446
447### OH_JSVM_TypeTagObject
448
449Associate the value of the **type_tag** pointer with a JS object so that the object can be identified more accurately.
450
451### OH_JSVM_CheckObjectTypeTag
452
453Checks whether a tag matches the tag type of an object.
454
455CPP code:
456
457```cpp
458// hello.cpp
459#include "napi/native_api.h"
460#include "ark_runtime/jsvm.h"
461#include <hilog/log.h>
462// Registers the SetTypeTagToObject and CheckObjectTypeTag callbacks.
463static JSVM_CallbackStruct param[] = {
464    {.data = nullptr, .callback = SetTypeTagToObject},
465    {.data = nullptr, .callback = CheckObjectTypeTag},
466};
467static JSVM_CallbackStruct *method = param;
468// Set property descriptors named setTypeTagToObject and CheckObjectTypeTag, and associate them with a callback each. This allows the SetTypeTagToObject and CheckObjectTypeTag callbacks to be called from JS.
469static JSVM_PropertyDescriptor descriptor[] = {
470    {"setTypeTagToObject", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
471    {"checkObjectTypeTag", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
472};
473#define NUMBERINT_FOUR 4
474// Define a static constant JSVM_TypeTag array to store type tags.
475static const JSVM_TypeTag TagsData[NUMBERINT_FOUR] = {
476    {0x9e4b2449547061b3, 0x33999f8a6516c499},
477    {0x1d55a794c53a726d, 0x43633f509f9c944e},
478    {0, 0}, // Indicates the default tag or no tag.
479    {0x6a971439f5b2e5d7, 0x531dc28a7e5317c0},
480};
481// Define OH_JSVM_TypeTagObject.
482static JSVM_Value SetTypeTagToObject(JSVM_Env env, JSVM_CallbackInfo info)
483{
484    // Obtain the two parameters passed from JS.
485    size_t argc = 2;
486    JSVM_Value args[2] = {nullptr};
487    OH_JSVM_GetCbInfo(env, info, &argc, args, nullptr, nullptr);
488    // Obtain the index number and convert it to JSVM_Value.
489    int32_t index = 0;
490    OH_JSVM_GetValueInt32(env, args[1], &index);
491    // Set the type tag for the parameter (object).
492    JSVM_Status status = OH_JSVM_TypeTagObject(env, args[0], &TagsData[index]);
493    if (status != JSVM_OK) {
494        OH_LOG_ERROR(LOG_APP, "JSVM SetTypeTagToObject fail");
495    } else {
496        OH_LOG_INFO(LOG_APP, "JSVM SetTypeTagToObject success");
497    }
498    // Convert the bool value to JSVM_Value and return it.
499    JSVM_Value result = nullptr;
500    OH_JSVM_GetBoolean(env, true, &result);
501    return result;
502}
503// Define OH_JSVM_CheckObjectTypeTag.
504static JSVM_Value CheckObjectTypeTag(JSVM_Env env, JSVM_CallbackInfo info)
505{
506    // Obtain the two parameters passed from JS.
507    size_t argc = 2;
508    JSVM_Value args[2] = {nullptr};
509    OH_JSVM_GetCbInfo(env, info, &argc, args, nullptr, nullptr);
510    // Obtain the index number and convert it to JSVM_Value.
511    int32_t index = 0;
512    OH_JSVM_GetValueInt32(env, args[1], &index);
513    // Check the type tag of the object.
514    bool checkResult = false;
515    JSVM_Status status = OH_JSVM_CheckObjectTypeTag(env, args[0], &TagsData[index], &checkResult);
516    if (status != JSVM_OK) {
517        OH_LOG_ERROR(LOG_APP, "JSVM SetTypeTagToObject fail");
518    } else {
519        OH_LOG_INFO(LOG_APP, "JSVM SetTypeTagToObject:%{public}d", checkResult);
520    }
521    // Convert the bool value to JSVM_Value and return it.
522    JSVM_Value checked = nullptr;
523    OH_JSVM_GetBoolean(env, checkResult, &checked);
524    return checked;
525}
526```
527
528ArkTS code:
529
530```ts
531import hilog from "@ohos.hilog"
532// Import the native APIs.
533import napitest from "libentry.so"
534let script: string = `
535         class Obj {
536           data;
537           message;
538         }
539         let obj= { data: 0, message: "hello world"};
540         setTypeTagToObject(obj, 0)
541       `
542try {
543  let result = napitest.runJsVm(script);
544  hilog.info(0x0000, 'JSVM', 'SetTypeTagToObject: %{public}s', result);
545} catch (error) {
546  hilog.error(0x0000, 'JSVM', 'SetTypeTagToObject: %{public}s', error.message);
547}
548let script: string = `
549         class Obj {
550           data;
551           message;
552         }
553         let obj= { data: 0, message: "hello world"};
554         setTypeTagToObject(obj,0)
555         checkObjectTypeTag(obj,0);
556       `
557try {
558  let result = napitest.runJsVm(script);
559  hilog.info(0x0000, 'JSVM', 'CheckObjectTypeTag: %{public}s', result);
560} catch (error) {
561  hilog.error(0x0000, 'JSVM', 'CheckObjectTypeTag: %{public}s', error.message);
562}
563```
564
565### OH_JSVM_CreateExternal
566
567Creates a JS object that wraps an external pointer.
568
569CPP code:
570
571```cpp
572// hello.cpp
573#include "napi/native_api.h"
574#include "ark_runtime/jsvm.h"
575#include <hilog/log.h>
576// Register the CreateExternal callback.
577static JSVM_CallbackStruct param[] = {
578    {.data = nullptr, .callback = CreateExternal},
579};
580static JSVM_CallbackStruct *method = param;
581// Set a property descriptor named createExternal and associate it with a callback. This allows the CreateExternal callback to be called from JS.
582static JSVM_PropertyDescriptor descriptor[] = {
583    {"createExternal", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
584};
585// Define OH_JSVM_CreateExternal.
586static JSVM_Value CreateExternal(JSVM_Env env, JSVM_CallbackInfo info)
587{
588    size_t dataSize = 10;
589    void *data = malloc(dataSize);
590    memset(data, 0, dataSize);
591    const char testStr[] = "test";
592    JSVM_Value external = nullptr;
593    JSVM_Status status = OH_JSVM_CreateExternal(
594        env, (void *)testStr, [](JSVM_Env env, void *data, void *hint) {}, (void *)testStr, &external);
595    JSVM_Value returnValue = nullptr;
596    bool type = false;
597    if (status != JSVM_OK) {
598        OH_LOG_ERROR(LOG_APP, "JSVM Failed to create external data, status:%{public}d.", status);
599        return nullptr;
600    } else {
601        type = true;
602        OH_LOG_INFO(LOG_APP, "JSVM CreateExternal:%{public}d", type);
603    }
604    OH_JSVM_GetBoolean(env, type, &returnValue);
605    // Return the result.
606    return returnValue;
607}
608```
609
610ArkTS code:
611
612```ts
613import hilog from "@ohos.hilog"
614// Import the native APIs.
615import napitest from "libentry.so"
616let script: string = `createExternal()`;
617try {
618  let result = napitest.runJsVm(script);
619  hilog.info(0x0000, 'testJSVM', 'Test JSVM createExternal: %{public}s', result);
620} catch (error) {
621  hilog.error(0x0000, 'testJSVM', 'Test JSVM createExternal error: %{public}s', error.message);
622}
623```
624
625### OH_JSVM_GetValueExternal
626
627Use **OH_JSVM_CreateExternal** to create a JS object that wraps a custom C/C++ object, and use **OH_JSVM_GetValueExternal** to obtain the custom C/C++ object from the JS object created by **OH_JSVM_CreateExternal**.
628
629CPP code:
630
631```cpp
632// hello.cpp
633#include "napi/native_api.h"
634#include "ark_runtime/jsvm.h"
635#include <hilog/log.h>
636// Register the GetValueExternal callback.
637static JSVM_CallbackStruct param[] = {
638    {.data = nullptr, .callback = GetValueExternal},
639};
640static JSVM_CallbackStruct *method = param;
641// Set a property descriptor named getValueExternal and associate it with a callback. This allows the GetValueExternal callback to be called from JS.
642static JSVM_PropertyDescriptor descriptor[] = {
643    {"getValueExternal", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
644};
645// Define OH_JSVM_GetValueExternal.
646static JSVM_Value GetValueExternal(JSVM_Env env, JSVM_CallbackInfo info)
647{
648    void *data = (void *)0x12345;
649    JSVM_Value externalValue = nullptr;
650    JSVM_Status status = OH_JSVM_CreateExternal(env, data, nullptr, nullptr, &externalValue);
651    if (status != JSVM_OK) {
652        OH_LOG_ERROR(LOG_APP, "JSVM OH_JSVM_CreateExternal fail");
653    }
654    void *data_value;
655    status = OH_JSVM_GetValueExternal(env, externalValue, &data_value);
656    bool type = false;
657    if (status != JSVM_OK) {
658        OH_LOG_ERROR(LOG_APP, "JSVM GetValueExternal fail");
659    }
660    type = true;
661    OH_LOG_INFO(LOG_APP, "JSVM API Get ValueExternal:%{public}p", data_value);
662    // Convert the sign bit into a value of int type and pass it.
663    JSVM_Value returnValue = nullptr;
664    OH_JSVM_CreateInt32(env, 0, &returnValue);
665    return returnValue;
666}
667```
668
669ArkTS code:
670
671```ts
672import hilog from "@ohos.hilog"
673// Import the native APIs.
674import napitest from "libentry.so"
675let script: string = `getValueExternal()`;
676try {
677  let result = napitest.runJsVm(script);
678  hilog.info(0x0000, 'testJSVM', 'Test JSVM getValueExternal: %{public}s', result);
679} catch (error) {
680  hilog.error(0x0000, 'testJSVM', 'Test JSVM getValueExternal error: %{public}s', error.message);
681}
682```
683
684### OH_JSVM_CreateSymbol
685
686Create a symbol. Symbol is a special data type used to indicate a unique identifier. Unlike strings or numbers, the value of a symbol is unique. Even if two symbols have the same description, they are not equal. Symbols are often used as keys for object properties to ensure property uniqueness.
687
688CPP code:
689
690```cpp
691// hello.cpp
692#include "napi/native_api.h"
693#include "ark_runtime/jsvm.h"
694#include <hilog/log.h>
695// Register the CreateSymbol callback.
696static JSVM_CallbackStruct param[] = {
697    {.data = nullptr, .callback = CreateSymbol},
698};
699static JSVM_CallbackStruct *method = param;
700// Set a property descriptor named createSymbol and associate it with a callback. This allows the CreateSymbol callback to be called from JS.
701static JSVM_PropertyDescriptor descriptor[] = {
702    {"createSymbol", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
703};
704// Define OH_JSVM_CreateSymbol.
705static JSVM_Value CreateSymbol(JSVM_Env env, JSVM_CallbackInfo info)
706{
707    JSVM_Value result = nullptr;
708    const char *des = "only";
709    OH_JSVM_CreateStringUtf8(env, des, JSVM_AUTO_LENGTH, &result);
710    JSVM_Value returnSymbol = nullptr;
711    OH_JSVM_CreateSymbol(env, result, &returnSymbol);
712    JSVM_Value returnValue = nullptr;
713    bool type = false;
714    JSVM_ValueType valuetypeSymbol;
715    OH_JSVM_Typeof(env, returnSymbol, &valuetypeSymbol);
716    if (valuetypeSymbol == JSVM_SYMBOL) {
717        OH_LOG_INFO(LOG_APP, "JSVM CreateSymbol Success");
718        type = true;
719    }
720    OH_JSVM_GetBoolean(env, type, &returnValue);
721    return returnValue;
722}
723```
724
725ArkTS code:
726
727```ts
728import hilog from "@ohos.hilog"
729// Import the native APIs.
730import napitest from "libentry.so"
731let script: string = `createSymbol()`;
732try {
733  let result = napitest.runJsVm(script);
734  hilog.info(0x0000, 'testJSVM', 'Test JSVM createSymbol: %{public}s', result);
735} catch (error) {
736  hilog.error(0x0000, 'testJSVM', 'Test JSVM createSymbol error: %{public}s', error.message);
737}
738```
739
740### OH_JSVM_SymbolFor
741
742Searches for a symbol with the given key in a global (runtime-wide) symbol registry. If a match is found, the symbol will be returned. Otherwise, a symbol will be created in the registry.
743
744CPP code:
745
746```cpp
747// hello.cpp
748#include "napi/native_api.h"
749#include "ark_runtime/jsvm.h"
750#include <hilog/log.h>
751// Register the SymbolFor callback.
752static JSVM_CallbackStruct param[] = {
753    {.data = nullptr, .callback = SymbolFor},
754};
755static JSVM_CallbackStruct *method = param;
756// Set a property descriptor named symbolFor and associate it with a callback. This allows the SymbolFor callback to be called from JS.
757static JSVM_PropertyDescriptor descriptor[] = {
758    {"symbolFor", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
759};
760// Define a constant to store the maximum length of a string.
761static const int MAX_BUFFER_SIZE = 128;
762// Define OH_JSVM_SymbolFor.
763static JSVM_Value SymbolFor(JSVM_Env env, JSVM_CallbackInfo info)
764{
765    JSVM_Value description = nullptr;
766    OH_JSVM_CreateStringUtf8(env, "test_demo", 9, &description);
767    char buffer[MAX_BUFFER_SIZE];
768    size_t bufferSize = MAX_BUFFER_SIZE;
769    size_t copied = 0;
770    OH_JSVM_GetValueStringUtf8(env, description, buffer, bufferSize, &copied);
771    JSVM_Value symbol = nullptr;
772    OH_JSVM_CreateSymbol(env, description, &symbol);
773    JSVM_Value result_symbol = nullptr;
774    JSVM_Status status = OH_JSVM_SymbolFor(env, nullptr, 0, &result_symbol);
775    JSVM_Value returnValue = nullptr;
776    bool type = false;
777    JSVM_ValueType valuetypeSymbol;
778    OH_JSVM_Typeof(env, result_symbol, &valuetypeSymbol);
779    if (valuetypeSymbol == JSVM_SYMBOL && status == JSVM_OK) {
780        OH_LOG_INFO(LOG_APP, "JSVM OH_JSVM_SymbolFor success");
781        type = true;
782    }
783    OH_JSVM_GetBoolean(env, type, &returnValue);
784    // Return the result.
785    return returnValue;
786}
787```
788
789ArkTS code:
790
791```ts
792import hilog from "@ohos.hilog"
793// Import the native APIs.
794import napitest from "libentry.so"
795let script: string = `symbolFor()`;
796try {
797  let result = napitest.runJsVm(script);
798  hilog.info(0x0000, 'testJSVM', 'Test JSVM symbolFor: %{public}s', result);
799} catch (error) {
800  hilog.error(0x0000, 'testJSVM', 'Test JSVM symbolFor error: %{public}s', error.message);
801}
802```
803