1# Error Handling Using JSVM-API
2
3## Introduction
4
5JSVM-API provides APIs for handling errors occurred in JavaScript (JS) code using exceptions. Properly using these APIs helps improve module stability and reliability.
6
7## Basic Concepts
8
9Exceptions and errors are common concepts in JS programming. An exception indicates the presence of an unexpected condition, and an error indicates that the application cannot perform certain operations correctly. JSVM-API provides a set of APIs for handling errors occurred in JS code using exceptions. Read on the following to learn basic concepts related to exception handling:
10
11- Exception: indicates an unexpected condition that may occur during the execution of an application. It can be a syntax error, runtime error, or logic error. For example, the division of a non-zero value with zero and an operation on undefined variables are exceptions.
12- Error: indicates that the application cannot perform some operations. Errors can be defined by the underlying system, API, or developer.
13- **TypeError**: indicates that the type of an operation or value does not meet the expectation. Generally, this error is caused by an incorrect data type.
14- **RangeError**: indicates that a value is not in the expected range. For example, an index beyond the array length is accessed.
15- **SyntaxError**: indicates a mistake in the syntax of a piece of code.
16
17These concepts are important in exception and error handling. Properly using methods to capture, handle, or report exceptions and errors help improve application stability. JSVM-API provides APIs for handling errors in JS code using exceptions.
18
19## Available APIs
20
21| API                      | Description                      |
22|----------------------------|--------------------------------|
23| OH_JSVM_CreateError, OH_JSVM_CreateTypeError, OH_JSVM_CreateRangeError, OH_JSVM_CreateSyntaxError| Creates a JS error.|
24| OH_JSVM_Throw | Throws a JS error object, which is created by **OH_JSVM_CreateError** or obtained by **OH_JSVM_GetLastErrorInfo**.|
25| OH_JSVM_ThrowError, OH_JSVM_ThrowTypeError, OH_JSVM_ThrowRangeError, OH_JSVM_ThrowSyntaxError| Throws a JS error object.|
26| OH_JSVM_IsError              | Checks whether the given **JSVM_Value** indicates an error.|
27| OH_JSVM_GetAndClearLastException    | Obtains and clears the last JS exception.|
28| OH_JSVM_IsExceptionPending   | Checks whether there is any pending exception.|
29
30## Example
31
32If you are just starting out with JSVM-API, see [JSVM-API Development Process](use-jsvm-process.md). The following demonstrates only the C++ code involved in error handling.
33
34### OH_JSVM_Throw
35
36Use **OH_JSVM_Throw** to throw a JS error object so that the error can be captured and handled.
37
38### OH_JSVM_CreateError
39
40Use **OH_JSVM_CreateError** to create a JS error object with text information.
41
42CPP code:
43
44```cpp
45// hello.cpp
46// Capture and clear the last exception in the JSVM environment and log the error message. This function is used as a public function and will not be declared or defined in subsequent examples in this document.
47static void GetLastErrorAndClean(JSVM_Env env) {
48    // Call OH_JSVM_GetAndClearLastException to obtain and clear the last exception. This API can also be used to handle a suspended JS exception.
49    JSVM_Value result = nullptr;
50    JSVM_Status status = OH_JSVM_GetAndClearLastException(env, &result);
51    // Log error information.
52    JSVM_Value message;
53    JSVM_Value errorCode;
54    OH_JSVM_GetNamedProperty((env), result, "message", &message);
55    OH_JSVM_GetNamedProperty((env), result, "code", &errorCode);
56    char messagestr[256];
57    char codeStr[256];
58    OH_JSVM_GetValueStringUtf8(env, message, messagestr, 256, nullptr);
59    OH_JSVM_GetValueStringUtf8(env, errorCode, codeStr, 256, nullptr);
60    OH_LOG_INFO(LOG_APP, "JSVM error message: %{public}s, error code: %{public}s", messagestr, codeStr);
61}
62
63// Define OH_JSVM_CreateError.
64static JSVM_Value JsVmCreateThrowError(JSVM_Env env, JSVM_CallbackInfo info) {
65    // Create a string in the JSVM and store it in the errorCode variable.
66    JSVM_Value errorCode = nullptr;
67    OH_JSVM_CreateStringUtf8(env, "-1", JSVM_AUTO_LENGTH, &errorCode);
68    // Create a string in the JSVM and store it in the errorMessage variable.
69    JSVM_Value errorMessage = nullptr;
70    OH_JSVM_CreateStringUtf8(env, "HasError", JSVM_AUTO_LENGTH, &errorMessage);
71    // Create a JS error object.
72    JSVM_Value error = nullptr;
73    OH_JSVM_CreateError(env, errorCode, errorMessage, &error);
74    // Call OH_JSVM_Throw to throw the error.
75    OH_JSVM_Throw(env, error);
76    GetLastErrorAndClean(env);
77    return nullptr;
78}
79
80// Register the JsVmCreateThrowError callback.
81static JSVM_CallbackStruct param[] = {
82    {.data = nullptr, .callback = JsVmCreateThrowError},
83};
84static JSVM_CallbackStruct *method = param;
85// Set a property descriptor named jsVmCreateThrowError and associate it with a callback. This allows the JsVmCreateThrowError callback to be called from JS.
86static JSVM_PropertyDescriptor descriptor[] = {
87    {"jsVmCreateThrowError", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
88};
89// Call the C++ code from JS.
90const char *srcCallNative = R"JS(jsVmCreateThrowError();)JS";
91```
92**Expected output**
93```ts
94JSVM error message: HasError, error code: -1
95```
96
97### OH_JSVM_ThrowError
98
99Use **OH_JSVM_ThrowError** to throw a JS **Error** object with text information.
100
101CPP code:
102
103```cpp
104// hello.cpp
105// Define OH_JSVM_ThrowError.
106static JSVM_Value JsVmThrowError(JSVM_Env env, JSVM_CallbackInfo info)
107{
108    size_t argc = 1;
109    JSVM_Value argv[1] = {nullptr};
110    OH_JSVM_GetCbInfo(env, info, &argc, argv, nullptr, nullptr);
111    if (argc == 0) {
112        // Throw an error if no parameter is passed in.
113        OH_JSVM_ThrowError(env, "-1", "has Error");
114    } else if (argc == 1) {
115        size_t length;
116        // Obtain the length of the string passed from JS from the input parameter.
117        OH_JSVM_GetValueStringUtf8(env, argv[0], nullptr, 0, &length);
118        char *buffer = new char[length + 1];
119        // Obtain the string of the input parameter.
120        OH_JSVM_GetValueStringUtf8(env, argv[0], buffer, length + 1, nullptr);
121        // Populate the error information to OH_JSVM_ThrowError.
122        OH_JSVM_ThrowError(env, "self defined error code", buffer);
123        delete[] buffer;
124    }
125    GetLastErrorAndClean(env);
126    return nullptr;
127}
128// Register the JsVmThrowError callback.
129static JSVM_CallbackStruct param[] = {
130    {.data = nullptr, .callback = JsVmThrowError},
131};
132static JSVM_CallbackStruct *method = param;
133// Set a property descriptor named jsVmThrowError and associate it with a callback. This allows the JsVmThrowError callback to be called from JS.
134static JSVM_PropertyDescriptor descriptor[] = {
135    {"jsVmThrowError", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
136};
137// Call the C++ code from JS.
138const char *srcCallNative = R"JS(jsVmThrowError();jsVmThrowError("self defined error message");)JS";
139```
140
141**Expected output**
142```ts
143JSVM error message: has Error, error code: -1
144JSVM error message: self defined error message, error code: self defined error code
145```
146
147### OH_JSVM_ThrowTypeError
148
149Use **OH_JSVM_CreateTypeError** to create a JS **TypeError** object with text information.
150
151CPP code:
152
153```cpp
154// hello.cpp
155// Define OH_JSVM_ThrowTypeError.
156static JSVM_Value JsVmThrowTypeError(JSVM_Env env, JSVM_CallbackInfo info) {
157    size_t argc = 1;
158    JSVM_Value argv[1] = {nullptr};
159    OH_JSVM_GetCbInfo(env, info, &argc, argv, nullptr, nullptr);
160    if (argc == 0) {
161        // Throw an error if no parameter is passed in.
162        OH_JSVM_ThrowTypeError(env, "-1", "throwing type error");
163    } else if (argc == 1) {
164        size_t length;
165        // Obtain the length of the string in the input parameter passed from JS.
166        OH_JSVM_GetValueStringUtf8(env, argv[0], nullptr, 0, &length);
167        char *buffer = new char[length + 1];
168        // Obtain the string of the input parameter.
169        OH_JSVM_GetValueStringUtf8(env, argv[0], buffer, length + 1, nullptr);
170        // Populate the error information to OH_JSVM_ThrowError.
171        OH_JSVM_ThrowTypeError(env, "self defined error code", buffer);
172        delete[] buffer;
173    }
174    GetLastErrorAndClean(env);
175    return nullptr;
176}
177// Register the **JsVmThrowTypeError** callback.
178static JSVM_CallbackStruct param[] = {
179    {.data = nullptr, .callback = JsVmThrowTypeError},
180};
181static JSVM_CallbackStruct *method = param;
182// Set a property descriptor named jsVmThrowTypeError and associate it with a callback. This allows the JsVmThrowTypeError callback to be called from JS.
183static JSVM_PropertyDescriptor descriptor[] = {
184    {"jsVmThrowTypeError", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
185};
186// Call the C++ code from JS.
187const char *srcCallNative = R"JS(jsVmThrowTypeError();jsVmThrowTypeError("self defined error message");)JS";
188```
189
190**Expected output**
191```ts
192JSVM error message: throwing type error, error code: -1
193JSVM error message: self defined error message, error code: self defined error code
194```
195
196### OH_JSVM_ThrowRangeError
197
198Use **OH_JSVM_CreateRangeError** to create a JS **RangeError** with text information.
199
200CPP code:
201
202```cpp
203// hello.cpp
204// Define OH_JSVM_ThrowRangeError.
205static JSVM_Value JsVmThrowRangeError(JSVM_Env env, JSVM_CallbackInfo info)
206{
207    // Pass two parameters from JS.
208    size_t argc = 2;
209    JSVM_Value argv[2] = {nullptr};
210    OH_JSVM_GetCbInfo(env, info, &argc, argv, nullptr, nullptr);
211    // If the number of parameters is not 2,
212    if (argc != 2) {
213        // Throw a RangeError.
214        OH_JSVM_ThrowRangeError(env, "OH_JSVM_ThrowRangeError", "Expected two numbers as arguments");
215        GetLastErrorAndClean(env);
216        return nullptr;
217    }
218    JSVM_Value result = nullptr;
219    OH_JSVM_GetBoolean(env, true, &result);
220    return result;
221}
222// Register the JsVmThrowRangeError callback.
223static JSVM_CallbackStruct param[] = {
224    {.data = nullptr, .callback = JsVmThrowRangeError},
225};
226static JSVM_CallbackStruct *method = param;
227// Set a property descriptor named jsVmThrowRangeError and associate it with a callback. This allows the JsVmThrowRangeError callback to be called from JS.
228static JSVM_PropertyDescriptor descriptor[] = {
229    {"jsVmThrowRangeError", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
230};
231// Call the C++ code from JS.
232const char *srcCallNative = R"JS(jsVmThrowRangeError(1);)JS";
233```
234
235
236**Expected output**
237```ts
238JSVM error message: Expected two numbers as arguments, error code: OH_JSVM_ThrowRangeError
239```
240
241### OH_JSVM_ThrowSyntaxError
242
243Use **OH_JSVM_ThrowSyntaxError** to create and throw a JS **SyntaxError** object with text information.
244
245CPP code:
246
247```cpp
248// hello.cpp
249// Define OH_JSVM_ThrowSyntaxError.
250static JSVM_Value JsVmThrowSyntaxError(JSVM_Env env, JSVM_CallbackInfo info) {
251    // Pass the JS code from JS.
252    size_t argc = 1;
253    JSVM_Value argv[1] = {nullptr};
254    OH_JSVM_GetCbInfo(env, info, &argc, argv, nullptr, nullptr);
255    JSVM_Script script = nullptr;
256    // Call OH_JSVM_CompileScript to compile the JS code.
257    OH_JSVM_CompileScript(env, argv[0], nullptr, 0, true, nullptr, &script);
258    JSVM_Value scriptResult = nullptr;
259    // Call OH_JSVM_RunScript to run the JS code.
260    JSVM_Status status = OH_JSVM_RunScript(env, script, &scriptResult);
261    if (status != JSVM_OK) {
262        // If the value returned by JSVM_RunScript is not JSVM_OK, throw a SyntaxError.
263        OH_JSVM_ThrowSyntaxError(env, "JsVmThrowSyntaxError", "throw syntax error");
264        GetLastErrorAndClean(env);
265        return nullptr;
266    }
267    JSVM_Value result = nullptr;
268    OH_JSVM_GetBoolean(env, true, &result);
269    return result;
270}
271// Register the JsVmThrowSyntaxError callback.
272static JSVM_CallbackStruct param[] = {
273    {.data = nullptr, .callback = JsVmThrowSyntaxError},
274};
275static JSVM_CallbackStruct *method = param;
276// Set a property descriptor named jsVmThrowSyntaxError and associate it with a callback. This allows the JsVmThrowSyntaxError callback to be called from JS.
277static JSVM_PropertyDescriptor descriptor[] = {
278    {"jsVmThrowSyntaxError", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
279};
280// Call the C++ code from JS.
281const char *srcCallNative = R"JS(jsVmThrowSyntaxError();)JS";
282```
283
284**Expected output**
285```ts
286JSVM error message: throw syntax error, error code: JsVmThrowSyntaxError
287```
288
289### OH_JSVM_IsError
290
291Use **OH_JSVM_IsError** to check whether the given **JSVM_Value** represents an error object.
292
293CPP code:
294
295```cpp
296// hello.cpp
297// Define OH_JSVM_IsError.
298static JSVM_Value JsVmIsError(JSVM_Env env, JSVM_CallbackInfo info) {
299    size_t argc = 1;
300    JSVM_Value args[1] = {nullptr};
301    OH_JSVM_GetCbInfo(env, info, &argc, args, nullptr, nullptr);
302    // Call OH_JSVM_IsError to check whether the input parameter is an error object.
303    bool result = false;
304    // If JSVM_Value is an error object, set result to true. Otherwise, set result to false.
305    JSVM_Status status = OH_JSVM_IsError(env, args[0], &result);
306    if (status == JSVM_OK) {
307        OH_LOG_INFO(LOG_APP, "JSVM API call OH_JSVM_IsError success, result is %{public}d", result);
308    }else {
309        OH_LOG_INFO(LOG_APP, "JSVM API call OH_JSVM_IsError failed");
310    }
311    // Obtain result, call OH_JSVM_GetBoolean to convert result to JSVM_Value, and return JSVM_Value.
312    JSVM_Value returnValue = nullptr;
313    OH_JSVM_GetBoolean(env, result, &returnValue);
314    return returnValue;
315}
316// Register the JsVmIsError callback.
317static JSVM_CallbackStruct param[] = {
318    {.data = nullptr, .callback = JsVmIsError},
319};
320static JSVM_CallbackStruct *method = param;
321// Set a property descriptor named OH_JSVM_IsError and associate it with a callback. This allows the JsVmIsError callback to be called from JS.
322static JSVM_PropertyDescriptor descriptor[] = {
323    {"jsVmIsError", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
324};
325// Call the C++ code from JS.
326const char *srcCallNative = R"JS(jsVmIsError(Error()))JS";
327```
328
329**Expected output**
330```ts
331JSVM API call OH_JSVM_IsError success, result is 1
332```
333
334### OH_JSVM_CreateTypeError
335
336Use **OH_JSVM_CreateTypeError** to create a JS **TypeError** object with text information.
337
338CPP code:
339
340```cpp
341// hello.cpp
342// Define OH_JSVM_CreateTypeError.
343static JSVM_Value JsVmCreateTypeError(JSVM_Env env, JSVM_CallbackInfo info) {
344    // Create a string in the JSVM and store it in the errorCode variable.
345    JSVM_Value errorCode = nullptr;
346    OH_JSVM_CreateStringUtf8(env, "-1", JSVM_AUTO_LENGTH, &errorCode);
347    // Create a string in the JSVM and store it in the errorMessage variable.
348    JSVM_Value errorMessage = nullptr;
349    OH_JSVM_CreateStringUtf8(env, "HasError", JSVM_AUTO_LENGTH, &errorMessage);
350    JSVM_Value result = nullptr;
351    JSVM_Status status = OH_JSVM_CreateTypeError(env, errorCode, errorMessage, &result);
352    if (status == JSVM_OK) {
353        OH_LOG_INFO(LOG_APP, "JSVM API Create TypeError SUCCESS");
354    } else {
355        OH_LOG_INFO(LOG_APP, "JSVM API Create TypeError FAILED");
356    }
357    return result;
358}
359// Register the JsVmCreateTypeError callback.
360static JSVM_CallbackStruct param[] = {
361    {.data = nullptr, .callback = JsVmCreateTypeError},
362};
363static JSVM_CallbackStruct *method = param;
364// Set a property descriptor named jsVmCreateTypeError and associate it with a callback. This allows the JsVmCreateTypeError callback to be called from JS.
365static JSVM_PropertyDescriptor descriptor[] = {
366    {"jsVmCreateTypeError", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
367};
368// Call the C++ code from JS.
369const char *srcCallNative = R"JS(jsVmCreateTypeError();)JS";
370```
371
372**Expected output**
373```ts
374JSVM API Create TypeError SUCCESS
375```
376
377### OH_JSVM_CreateRangeError
378
379Use **OH_JSVM_CreateRangeError** to create a JS **RangeError** with text information.
380
381CPP code:
382
383```cpp
384// hello.cpp
385// Define OH_JSVM_CreateRangeError.
386static JSVM_Value JsVmCreateRangeError(JSVM_Env env, JSVM_CallbackInfo info) {
387    // Create a string in the JSVM and store it in the errorCode variable.
388    JSVM_Value errorCode = nullptr;
389    OH_JSVM_CreateStringUtf8(env, "-1", JSVM_AUTO_LENGTH, &errorCode);
390    // Create a string in the JSVM and store it in the errorMessage variable.
391    JSVM_Value errorMessage = nullptr;
392    OH_JSVM_CreateStringUtf8(env, "HasError", JSVM_AUTO_LENGTH, &errorMessage);
393    JSVM_Value result = nullptr;
394    JSVM_Status status = OH_JSVM_CreateRangeError(env, errorCode, errorMessage, &result);
395    if (status == JSVM_OK) {
396        OH_LOG_INFO(LOG_APP, "JSVM API CreateRangeError SUCCESS");
397    } else {
398        OH_LOG_INFO(LOG_APP, "JSVM API CreateRangeError FAILED");
399    }
400    return result;
401}
402// Register the JsVmCreateRangeError callback.
403static JSVM_CallbackStruct param[] = {
404    {.data = nullptr, .callback = JsVmCreateRangeError},
405};
406static JSVM_CallbackStruct *method = param;
407// Set a property descriptor named jsVmCreateRangeError and associate it with a callback. This allows the JsVmCreateRangeError callback to be called from JS.
408static JSVM_PropertyDescriptor descriptor[] = {
409    {"jsVmCreateRangeError", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
410};
411// Call the C++ code from JS.
412const char *srcCallNative = R"JS(jsVmCreateRangeError();)JS";
413```
414
415**Expected output**
416```ts
417JSVM API CreateRangeError SUCCESS
418```
419### OH_JSVM_CreateSyntaxError
420
421Use **OH_JSVM_CreateSyntaxError** to create and throw a JS **SyntaxError** object with text information.
422
423CPP code:
424
425```cpp
426// hello.cpp
427// Define OH_JSVM_CreateSyntaxError.
428static JSVM_Value JsVmCreateSyntaxError(JSVM_Env env, JSVM_CallbackInfo info) {
429    // Create a string in the JSVM and store it in the errorCode variable.
430    JSVM_Value errorCode = nullptr;
431    OH_JSVM_CreateStringUtf8(env, "-1", JSVM_AUTO_LENGTH, &errorCode);
432    // Create a string in the JSVM and store it in the errorMessage variable.
433    JSVM_Value errorMessage = nullptr;
434    OH_JSVM_CreateStringUtf8(env, "HasError", JSVM_AUTO_LENGTH, &errorMessage);
435    JSVM_Value result = nullptr;
436    JSVM_Status status =  OH_JSVM_CreateSyntaxError(env, errorCode, errorMessage, &result);
437    if (status == JSVM_OK) {
438        OH_LOG_INFO(LOG_APP, "JSVM API CreateSyntaxError SUCCESS");
439    } else {
440        OH_LOG_INFO(LOG_APP, "JSVM API CreateSyntaxError FAILED");
441    }
442    return result;
443}
444// Register the JsVmCreateSyntaxError callback.
445static JSVM_CallbackStruct param[] = {
446    {.data = nullptr, .callback = JsVmCreateSyntaxError},
447};
448static JSVM_CallbackStruct *method = param;
449// Set a property descriptor named jsVmCreateThrowError and associate it with a callback. This allows the JsVmCreateThrowError callback to be called from JS.
450static JSVM_PropertyDescriptor descriptor[] = {
451    {"jsVmCreateSyntaxError", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
452};
453// Call the C++ code from JS.
454const char *srcCallNative = R"JS(jsVmCreateSyntaxError();)JS";
455```
456
457**Expected output**
458```ts
459JSVM API CreateSyntaxError SUCCESS
460```
461
462### OH_JSVM_GetAndClearLastException
463
464Use **OH_JSVM_GetAndClearLastException** to obtain and clear the latest exception.
465
466CPP code:
467
468```cpp
469// hello.cpp
470// Define OH_JSVM_GetAndClearLastException.
471static JSVM_Value JsVmGetAndClearLastException(JSVM_Env env, JSVM_CallbackInfo info) {
472    // Throw an error.
473    OH_JSVM_ThrowError(env, "OH_JSVM_ThrowError errorCode", "OH_JSVM_ThrowError errorMessage");
474    // Call OH_JSVM_GetAndClearLastException to obtain and clear the last exception. This API can also be used to handle a suspended JS exception.
475    JSVM_Value result = nullptr;
476    JSVM_Status status = OH_JSVM_GetAndClearLastException(env, &result);
477    if (status != JSVM_OK) {
478        OH_LOG_INFO(LOG_APP, "JSVM API OH_JSVM_GetAndClearLastException FAILED");
479    } else {
480        OH_LOG_INFO(LOG_APP, "JSVM API OH_JSVM_GetAndClearLastException SUCCESS");
481    }
482    return result;
483}
484// Register the JsVmGetAndClearLastException callback.
485static JSVM_CallbackStruct param[] = {
486    {.data = nullptr, .callback = JsVmGetAndClearLastException},
487};
488static JSVM_CallbackStruct *method = param;
489// Set a property descriptor named jsVmGetAndClearLastException and associate it with a callback. This allows the JsVmGetAndClearLastException callback to be called from JS.
490static JSVM_PropertyDescriptor descriptor[] = {
491    {"jsVmGetAndClearLastException", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
492};
493// Call the C++ code from JS.
494const char *srcCallNative = R"JS(jsVmGetAndClearLastException();)JS";
495```
496
497**Expected output**
498```ts
499JSVM API OH_JSVM_GetAndClearLastException SUCCESS
500```
501
502### OH_JSVM_IsExceptionPending
503
504Use **OH_JSVM_IsExceptionPending** to check whether there is any pending exception.
505
506CPP code:
507
508```cpp
509// hello.cpp
510// Define OH_JSVM_GetAndClearLastException.
511static JSVM_Value JsVmIsExceptionPending(JSVM_Env env, JSVM_CallbackInfo info) {
512    JSVM_Status status;
513    bool isExceptionPending = false;
514    // Perform operations that may cause an error.
515    OH_JSVM_ThrowError(env, "OH_JSVM_ThrowError errorCode", "OH_JSVM_ThrowError errorMessage");
516    // Check whether there is a pending exception.
517    status = OH_JSVM_IsExceptionPending(env, &isExceptionPending);
518    if (status != JSVM_OK) {
519        return nullptr;
520    }
521    if (isExceptionPending) {
522        OH_LOG_INFO(LOG_APP, "JSVM API OH_JSVM_IsExceptionPending: SUCCESS");
523        // Handle the pending exception.
524        JSVM_Value result = nullptr;
525        status = OH_JSVM_GetAndClearLastException(env, &result);
526        if (status != JSVM_OK) {
527            return nullptr;
528        }
529        // Return the result.
530        return result;
531    } else {
532        OH_LOG_INFO(LOG_APP, "JSVM API OH_JSVM_IsExceptionPending: FAILED");
533    }
534    return nullptr;
535}
536// Register the JsVmIsExceptionPending callback.
537static JSVM_CallbackStruct param[] = {
538    {.data = nullptr, .callback = JsVmIsExceptionPending},
539};
540static JSVM_CallbackStruct *method = param;
541// Set a property descriptor named jsVmIsExceptionPending and associate it with a callback. This allows the JsVmIsExceptionPending callback to be called from JS.
542static JSVM_PropertyDescriptor descriptor[] = {
543    {"jsVmIsExceptionPending", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
544};
545// Call the C++ code from JS.
546const char *srcCallNative = R"JS(jsVmIsExceptionPending();)JS";
547```
548
549**Expected output**
550```ts
551JSVM API OH_JSVM_IsExceptionPending: SUCCESS
552```
553
554### OH_JSVM_GetLastErrorInfo
555
556Use **OH_JSVM_GetLastErrorInfo** to obtain the last error information (the return value is not **JSVM_OK**), including the error code, error message, and stack information. This API can also be used for suspended JS errors.
557Note that the errors triggered by APIs such as **OH_JSVM_ThrowError** will not be captured by the APIs unless the return value is not **JSVM_OK**.
558
559CPP code:
560
561```cpp
562// hello.cpp
563// Define OH_JSVM_GetLastErrorInfo.
564static JSVM_Value JsVmGetLastErrorInfo(JSVM_Env env, JSVM_CallbackInfo info) {
565    // Obtain the input parameter, that is the message string in this example.
566    size_t argc = 1;
567    JSVM_Value args[1] = {nullptr};
568    OH_JSVM_GetCbInfo(env, info, &argc, args, nullptr, nullptr);
569    // Call OH_JSVM_GetValueInt32 to obtain the input string parameter to create an error.
570    int32_t value = 0;
571    OH_JSVM_GetValueInt32(env, args[0], &value);
572    // Call OH_JSVM_GetLastErrorInfo to obtain the last error message.
573    const JSVM_ExtendedErrorInfo *errorInfo;
574    OH_JSVM_GetLastErrorInfo(env, &errorInfo);
575
576    // Obtain the error message as the return value and print it.
577    JSVM_Value result = nullptr;
578    OH_LOG_INFO(LOG_APP,
579                "JSVM API OH_JSVM_GetLastErrorInfo: SUCCESS, error message is %{public}s, error code is %{public}d",
580                errorInfo->errorMessage, errorInfo->errorCode);
581    // Handle the exception to prevent the application from exiting due to the error thrown.
582    JSVM_Value result1 = nullptr;
583    OH_JSVM_GetAndClearLastException(env, &result1);
584    OH_JSVM_CreateInt32(env, errorInfo->errorCode, &result);
585    return result;
586}
587// Register the JsVmGetLastErrorInfo callback.
588static JSVM_CallbackStruct param[] = {
589    {.data = nullptr, .callback = JsVmGetLastErrorInfo},
590};
591static JSVM_CallbackStruct *method = param;
592// Set a property descriptor named jsVmGetLastErrorInfo and associate it with a callback. This allows the JsVmGetLastErrorInfo callback to be called from JS.
593static JSVM_PropertyDescriptor descriptor[] = {
594    {"jsVmGetLastErrorInfo", nullptr, method++, nullptr, nullptr, nullptr, JSVM_DEFAULT},
595};
596// Call the C++ code from JS.
597const char *srcCallNative = R"JS(jsVmGetLastErrorInfo();)JS";}
598```
599
600**Expected output**
601```ts
602JSVM API OH_JSVM_GetLastErrorInfo: SUCCESS, error message is A number was expected, error code is 6
603```
604