1 /*
2  * Copyright (c) 2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  * http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "napi_webview_controller.h"
17 
18 #include <arpa/inet.h>
19 #include <cctype>
20 #include <climits>
21 #include <cstdint>
22 #include <regex>
23 #include <securec.h>
24 #include <unistd.h>
25 #include <uv.h>
26 
27 #include "application_context.h"
28 #include "business_error.h"
29 #include "napi_parse_utils.h"
30 #include "native_engine/native_engine.h"
31 #include "nweb.h"
32 #include "nweb_adapter_helper.h"
33 #include "nweb_helper.h"
34 #include "nweb_init_params.h"
35 #include "nweb_log.h"
36 #include "ohos_adapter_helper.h"
37 #include "parameters.h"
38 #include "pixel_map.h"
39 #include "pixel_map_napi.h"
40 #include "web_errors.h"
41 #include "webview_javascript_execute_callback.h"
42 #include "webview_createpdf_execute_callback.h"
43 
44 #include "web_download_delegate.h"
45 #include "web_download_manager.h"
46 #include "arkweb_scheme_handler.h"
47 #include "web_scheme_handler_request.h"
48 
49 namespace OHOS {
50 namespace NWeb {
51 using namespace NWebError;
52 using NWebError::NO_ERROR;
53 
54 namespace {
55 constexpr uint32_t URL_MAXIMUM = 2048;
56 constexpr uint32_t SOCKET_MAXIMUM = 6;
57 constexpr char URL_REGEXPR[] = "^http(s)?:\\/\\/.+";
58 constexpr size_t MAX_RESOURCES_COUNT = 30;
59 constexpr size_t MAX_RESOURCE_SIZE = 10 * 1024 * 1024;
60 constexpr size_t MAX_URL_TRUST_LIST_STR_LEN = 10 * 1024 * 1024; // 10M
61 constexpr double A4_WIDTH = 8.27;
62 constexpr double A4_HEIGHT = 11.69;
63 constexpr double SCALE_MIN = 0.1;
64 constexpr double SCALE_MAX = 2.0;
65 constexpr double HALF = 2.0;
66 constexpr double TEN_MILLIMETER_TO_INCH = 0.39;
67 constexpr size_t BFCACHE_DEFAULT_SIZE = 1;
68 constexpr size_t BFCACHE_DEFAULT_TIMETOLIVE = 600;
69 using WebPrintWriteResultCallback = std::function<void(std::string, uint32_t)>;
70 
ParsePrepareUrl(napi_env env, napi_value urlObj, std::string& url)71 bool ParsePrepareUrl(napi_env env, napi_value urlObj, std::string& url)
72 {
73     napi_valuetype valueType = napi_null;
74     napi_typeof(env, urlObj, &valueType);
75 
76     if (valueType == napi_string) {
77         NapiParseUtils::ParseString(env, urlObj, url);
78         if (url.size() > URL_MAXIMUM) {
79             WVLOG_E("The URL exceeds the maximum length of %{public}d", URL_MAXIMUM);
80             return false;
81         }
82 
83         if (!regex_match(url, std::regex(URL_REGEXPR, std::regex_constants::icase))) {
84             WVLOG_E("ParsePrepareUrl error");
85             return false;
86         }
87 
88         return true;
89     }
90 
91     WVLOG_E("Unable to parse type from url object.");
92     return false;
93 }
94 
ParseIP(napi_env env, napi_value urlObj, std::string& ip)95 bool ParseIP(napi_env env, napi_value urlObj, std::string& ip)
96 {
97     napi_valuetype valueType = napi_null;
98     napi_typeof(env, urlObj, &valueType);
99 
100     if (valueType == napi_string) {
101         NapiParseUtils::ParseString(env, urlObj, ip);
102         if (ip == "") {
103             WVLOG_E("The IP is null");
104             return false;
105         }
106 
107         unsigned char buf[sizeof(struct in6_addr)];
108         if ((inet_pton(AF_INET, ip.c_str(), buf) == 1) || (inet_pton(AF_INET6, ip.c_str(), buf) == 1)) {
109             return true;
110         }
111         WVLOG_E("IP error.");
112         return false;
113     }
114 
115     WVLOG_E("Unable to parse type from ip object.");
116     return false;
117 }
118 
GetArrayValueType(napi_env env, napi_value array, bool& isDouble)119 napi_valuetype GetArrayValueType(napi_env env, napi_value array, bool& isDouble)
120 {
121     uint32_t arrayLength = 0;
122     napi_get_array_length(env, array, &arrayLength);
123     napi_valuetype valueTypeFirst = napi_undefined;
124     napi_valuetype valueTypeCur = napi_undefined;
125     for (uint32_t i = 0; i < arrayLength; ++i) {
126         napi_value obj = nullptr;
127         napi_get_element(env, array, i, &obj);
128         napi_typeof(env, obj, &valueTypeCur);
129         if (i == 0) {
130             valueTypeFirst = valueTypeCur;
131         }
132         if (valueTypeCur != napi_string && valueTypeCur != napi_number && valueTypeCur != napi_boolean) {
133             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
134             return napi_undefined;
135         }
136         if (valueTypeCur != valueTypeFirst) {
137             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
138             return napi_undefined;
139         }
140         if (valueTypeFirst == napi_number) {
141             int32_t elementInt32 = 0;
142             double elementDouble = 0.0;
143             bool isReadValue32 = napi_get_value_int32(env, obj, &elementInt32) == napi_ok;
144             bool isReadDouble = napi_get_value_double(env, obj, &elementDouble) == napi_ok;
145             constexpr double MINIMAL_ERROR = 0.000001;
146             if (isReadValue32 && isReadDouble) {
147                 isDouble = abs(elementDouble - elementInt32 * 1.0) > MINIMAL_ERROR;
148             } else if (isReadDouble) {
149                 isDouble = true;
150             }
151         }
152     }
153     return valueTypeFirst;
154 }
155 
SetArrayHandlerBoolean(napi_env env, napi_value array, WebMessageExt* webMessageExt)156 void SetArrayHandlerBoolean(napi_env env, napi_value array, WebMessageExt* webMessageExt)
157 {
158     std::vector<bool> outValue;
159     if (!NapiParseUtils::ParseBooleanArray(env, array, outValue)) {
160         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
161         return;
162     }
163     webMessageExt->SetBooleanArray(outValue);
164 }
165 
SetArrayHandlerString(napi_env env, napi_value array, WebMessageExt* webMessageExt)166 void SetArrayHandlerString(napi_env env, napi_value array, WebMessageExt* webMessageExt)
167 {
168     std::vector<std::string> outValue;
169     if (!NapiParseUtils::ParseStringArray(env, array, outValue)) {
170         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
171         return;
172     }
173     webMessageExt->SetStringArray(outValue);
174 }
175 
SetArrayHandlerInteger(napi_env env, napi_value array, WebMessageExt* webMessageExt)176 void SetArrayHandlerInteger(napi_env env, napi_value array, WebMessageExt* webMessageExt)
177 {
178     std::vector<int64_t> outValue;
179     if (!NapiParseUtils::ParseInt64Array(env, array, outValue)) {
180         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
181         return;
182     }
183     webMessageExt->SetInt64Array(outValue);
184 }
185 
SetArrayHandlerDouble(napi_env env, napi_value array, WebMessageExt* webMessageExt)186 void SetArrayHandlerDouble(napi_env env, napi_value array, WebMessageExt* webMessageExt)
187 {
188     std::vector<double> outValue;
189     if (!NapiParseUtils::ParseDoubleArray(env, array, outValue)) {
190         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
191         return;
192     }
193     webMessageExt->SetDoubleArray(outValue);
194 }
195 
GetWebviewController(napi_env env, napi_callback_info info)196 WebviewController* GetWebviewController(napi_env env, napi_callback_info info)
197 {
198     napi_value thisVar = nullptr;
199     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
200 
201     WebviewController *webviewController = nullptr;
202     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
203     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
204         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
205         return nullptr;
206     }
207     return webviewController;
208 }
209 
ParsePrepareRequestMethod(napi_env env, napi_value methodObj, std::string& method)210 bool ParsePrepareRequestMethod(napi_env env, napi_value methodObj, std::string& method)
211 {
212     napi_valuetype valueType = napi_null;
213     napi_typeof(env, methodObj, &valueType);
214 
215     if (valueType == napi_string) {
216         NapiParseUtils::ParseString(env, methodObj, method);
217         if (method != "POST") {
218             WVLOG_E("The method %{public}s is not supported.", method.c_str());
219             return false;
220         }
221         return true;
222     }
223 
224     WVLOG_E("Unable to parse type from method object.");
225     return false;
226 }
227 
ParseHttpHeaders(napi_env env, napi_value headersArray, std::map<std::string, std::string>* headers)228 bool ParseHttpHeaders(napi_env env, napi_value headersArray, std::map<std::string, std::string>* headers)
229 {
230     bool isArray = false;
231     napi_is_array(env, headersArray, &isArray);
232     if (isArray) {
233         uint32_t arrayLength = INTEGER_ZERO;
234         napi_get_array_length(env, headersArray, &arrayLength);
235         for (uint32_t i = 0; i < arrayLength; ++i) {
236             std::string key;
237             std::string value;
238             napi_value obj = nullptr;
239             napi_value keyObj = nullptr;
240             napi_value valueObj = nullptr;
241             napi_get_element(env, headersArray, i, &obj);
242             if (napi_get_named_property(env, obj, "headerKey", &keyObj) != napi_ok) {
243                 continue;
244             }
245             if (napi_get_named_property(env, obj, "headerValue", &valueObj) != napi_ok) {
246                 continue;
247             }
248             if (!NapiParseUtils::ParseString(env, keyObj, key) || !NapiParseUtils::ParseString(env, valueObj, value)) {
249                 WVLOG_E("Unable to parse string from headers array object.");
250                 return false;
251             }
252             if (key.empty()) {
253                 WVLOG_E("Key from headers is empty.");
254                 return false;
255             }
256             (*headers)[key] = value;
257         }
258     } else {
259         WVLOG_E("Unable to parse type from headers array object.");
260         return false;
261     }
262     return true;
263 }
264 
CheckCacheKey(napi_env env, const std::string& cacheKey)265 bool CheckCacheKey(napi_env env, const std::string& cacheKey)
266 {
267     for (char c : cacheKey) {
268         if (!isalnum(c)) {
269             WVLOG_E("BusinessError: 401. The character of 'cacheKey' must be number or letters.");
270             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
271             return false;
272         }
273     }
274     return true;
275 }
276 
ParseCacheKeyList(napi_env env, napi_value cacheKeyArray, std::vector<std::string>* cacheKeyList)277 bool ParseCacheKeyList(napi_env env, napi_value cacheKeyArray, std::vector<std::string>* cacheKeyList)
278 {
279     bool isArray = false;
280     napi_is_array(env, cacheKeyArray, &isArray);
281     if (!isArray) {
282         WVLOG_E("Unable to parse type from CacheKey array object.");
283         return false;
284     }
285     uint32_t arrayLength = INTEGER_ZERO;
286     napi_get_array_length(env, cacheKeyArray, &arrayLength);
287     if (arrayLength == 0) {
288         WVLOG_E("cacheKey array length is invalid");
289         return false;
290     }
291     for (uint32_t i = 0; i < arrayLength; ++i) {
292         napi_value cacheKeyItem = nullptr;
293         napi_get_element(env, cacheKeyArray, i, &cacheKeyItem);
294         std::string cacheKeyStr;
295         if (!NapiParseUtils::ParseString(env, cacheKeyItem, cacheKeyStr)) {
296             WVLOG_E("Unable to parse string from cacheKey array object.");
297             return false;
298         }
299         if (cacheKeyStr.empty()) {
300             WVLOG_E("Cache Key is empty.");
301             return false;
302         }
303         for (char c : cacheKeyStr) {
304             if (!isalnum(c)) {
305                 WVLOG_E("Cache Key is invalid.");
306                 return false;
307             }
308         }
309         cacheKeyList->emplace_back(cacheKeyStr);
310     }
311     return true;
312 }
313 
ParsePrefetchArgs(napi_env env, napi_value preArgs)314 std::shared_ptr<NWebEnginePrefetchArgs> ParsePrefetchArgs(napi_env env, napi_value preArgs)
315 {
316     napi_value urlObj = nullptr;
317     std::string url;
318     napi_get_named_property(env, preArgs, "url", &urlObj);
319     if (!ParsePrepareUrl(env, urlObj, url)) {
320         BusinessError::ThrowErrorByErrcode(env, INVALID_URL);
321         return nullptr;
322     }
323 
324     napi_value methodObj = nullptr;
325     std::string method;
326     napi_get_named_property(env, preArgs, "method", &methodObj);
327     if (!ParsePrepareRequestMethod(env, methodObj, method)) {
328         WVLOG_E("BusinessError: 401. The type of 'method' must be string 'POST'.");
329         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
330         return nullptr;
331     }
332 
333     napi_value formDataObj = nullptr;
334     std::string formData;
335     napi_get_named_property(env, preArgs, "formData", &formDataObj);
336     if (!NapiParseUtils::ParseString(env, formDataObj, formData)) {
337         WVLOG_E("BusinessError: 401. The type of 'formData' must be string.");
338         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
339         return nullptr;
340     }
341     std::shared_ptr<NWebEnginePrefetchArgs> prefetchArgs = std::make_shared<NWebEnginePrefetchArgsImpl>(
342         url, method, formData);
343     return prefetchArgs;
344 }
345 
ParsePDFMarginConfigArgs(napi_env env, napi_value preArgs, double width, double height)346 PDFMarginConfig ParsePDFMarginConfigArgs(napi_env env, napi_value preArgs, double width, double height)
347 {
348     napi_value marginTopObj = nullptr;
349     double marginTop = TEN_MILLIMETER_TO_INCH;
350     napi_get_named_property(env, preArgs, "marginTop", &marginTopObj);
351     if (!NapiParseUtils::ParseDouble(env, marginTopObj, marginTop)) {
352         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
353             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "marginTop", "number"));
354         return PDFMarginConfig();
355     }
356     marginTop = (marginTop >= height / HALF || marginTop <= 0.0) ? 0.0 : marginTop;
357 
358     napi_value marginBottomObj = nullptr;
359     double marginBottom = TEN_MILLIMETER_TO_INCH;
360     napi_get_named_property(env, preArgs, "marginBottom", &marginBottomObj);
361     if (!NapiParseUtils::ParseDouble(env, marginBottomObj, marginBottom)) {
362         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
363             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "marginBottom", "number"));
364         return PDFMarginConfig();
365     }
366     marginBottom = (marginBottom >= height / HALF || marginBottom <= 0.0) ? 0.0 : marginBottom;
367 
368     napi_value marginRightObj = nullptr;
369     double marginRight = TEN_MILLIMETER_TO_INCH;
370     napi_get_named_property(env, preArgs, "marginRight", &marginRightObj);
371     if (!NapiParseUtils::ParseDouble(env, marginRightObj, marginRight)) {
372         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
373             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "marginRight", "number"));
374         return PDFMarginConfig();
375     }
376     marginRight = (marginRight >= width / HALF || marginRight <= 0.0) ? 0.0 : marginRight;
377 
378     napi_value marginLeftObj = nullptr;
379     double marginLeft = TEN_MILLIMETER_TO_INCH;
380     napi_get_named_property(env, preArgs, "marginLeft", &marginLeftObj);
381     if (!NapiParseUtils::ParseDouble(env, marginLeftObj, marginLeft)) {
382         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
383             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "marginLeft", "number"));
384         return PDFMarginConfig();
385     }
386     marginLeft = (marginLeft >= width / HALF || marginLeft <= 0.0) ? 0.0 : marginLeft;
387 
388     return { marginTop, marginBottom, marginRight, marginLeft };
389 }
390 
ParsePDFConfigArgs(napi_env env, napi_value preArgs)391 std::shared_ptr<NWebPDFConfigArgs> ParsePDFConfigArgs(napi_env env, napi_value preArgs)
392 {
393     napi_value widthObj = nullptr;
394     double width = A4_WIDTH;
395     napi_get_named_property(env, preArgs, "width", &widthObj);
396     if (!NapiParseUtils::ParseDouble(env, widthObj, width)) {
397         BusinessError::ThrowErrorByErrcode(
398             env, PARAM_CHECK_ERROR, NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "width", "number"));
399         return nullptr;
400     }
401 
402     napi_value heightObj = nullptr;
403     double height = A4_HEIGHT;
404     napi_get_named_property(env, preArgs, "height", &heightObj);
405     if (!NapiParseUtils::ParseDouble(env, heightObj, height)) {
406         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
407             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "height", "number"));
408         return nullptr;
409     }
410 
411     napi_value scaleObj = nullptr;
412     double scale = 1.0;
413     napi_get_named_property(env, preArgs, "scale", &scaleObj);
414     NapiParseUtils::ParseDouble(env, scaleObj, scale);
415     scale = scale > SCALE_MAX ? SCALE_MAX : scale < SCALE_MIN ? SCALE_MIN : scale;
416 
417     auto margin = ParsePDFMarginConfigArgs(env, preArgs, width, height);
418 
419     napi_value shouldPrintBackgroundObj = nullptr;
420     bool shouldPrintBackground = false;
421     napi_get_named_property(env, preArgs, "shouldPrintBackground", &shouldPrintBackgroundObj);
422     NapiParseUtils::ParseBoolean(env, shouldPrintBackgroundObj, shouldPrintBackground);
423 
424     std::shared_ptr<NWebPDFConfigArgs> pdfConfig = std::make_shared<NWebPDFConfigArgsImpl>(
425         width, height, scale, margin.top, margin.bottom, margin.right, margin.left, shouldPrintBackground);
426     return pdfConfig;
427 }
428 
429 void JsErrorCallback(napi_env env, napi_ref jsCallback, int32_t err)
430 {
431     napi_value jsError = nullptr;
432     napi_value jsResult = nullptr;
433 
434     jsError = BusinessError::CreateError(env, err);
435     napi_get_undefined(env, &jsResult);
436     napi_value args[INTEGER_TWO] = {jsError, jsResult};
437 
438     napi_value callback = nullptr;
439     napi_value callbackResult = nullptr;
440     napi_get_reference_value(env, jsCallback, &callback);
441     napi_call_function(env, nullptr, callback, INTEGER_TWO, args, &callbackResult);
442     napi_delete_reference(env, jsCallback);
443 }
444 
445 bool ParseRegisterJavaScriptProxyParam(napi_env env, size_t argc, napi_value* argv,
446     RegisterJavaScriptProxyParam* param)
447 {
448     std::string objName;
449     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ONE], objName)) {
450         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
451             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "name", "string"));
452         return false;
453     }
454     std::vector<std::string> methodList;
455     if (!NapiParseUtils::ParseStringArray(env, argv[INTEGER_TWO], methodList)) {
456         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
457             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "methodList", "array"));
458         return false;
459     }
460     std::vector<std::string> asyncMethodList;
461     if (argc == INTEGER_FOUR && !NapiParseUtils::ParseStringArray(env, argv[INTEGER_THREE], asyncMethodList)) {
462         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
463         return false;
464     }
465     std::string permission;
466     if (argc == INTEGER_FIVE && !NapiParseUtils::ParseString(env, argv[INTEGER_FOUR], permission)) {
467         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
468             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "permission", "string"));
469         return false;
470     }
471     param->env = env;
472     param->obj = argv[INTEGER_ZERO];
473     param->objName = objName;
474     param->syncMethodList = methodList;
475     param->asyncMethodList = asyncMethodList;
476     param->permission = permission;
477     return true;
478 }
479 
RemoveDownloadDelegateRef(napi_env env, napi_value thisVar)480 napi_value RemoveDownloadDelegateRef(napi_env env, napi_value thisVar)
481 {
482     WebviewController *webviewController = nullptr;
483     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webviewController));
484     if (webviewController == nullptr || !webviewController->IsInit()) {
485         WVLOG_E("create message port failed, napi unwrap webviewController failed");
486         return nullptr;
487     }
488 
489     WebDownloadManager::RemoveDownloadDelegateRef(webviewController->GetWebId());
490     return nullptr;
491 }
492 
493 } // namespace
494 
495 int32_t NapiWebviewController::maxFdNum_ = -1;
496 std::atomic<int32_t> NapiWebviewController::usedFd_ {0};
497 std::atomic<bool> g_inWebPageSnapshot {false};
498 
499 thread_local napi_ref g_classWebMsgPort;
500 thread_local napi_ref g_historyListRef;
501 thread_local napi_ref g_webMsgExtClassRef;
502 thread_local napi_ref g_webPrintDocClassRef;
Init(napi_env env, napi_value exports)503 napi_value NapiWebviewController::Init(napi_env env, napi_value exports)
504 {
505     napi_property_descriptor properties[] = {
506         DECLARE_NAPI_STATIC_FUNCTION("initializeWebEngine", NapiWebviewController::InitializeWebEngine),
507         DECLARE_NAPI_STATIC_FUNCTION("setHttpDns", NapiWebviewController::SetHttpDns),
508         DECLARE_NAPI_STATIC_FUNCTION("setWebDebuggingAccess", NapiWebviewController::SetWebDebuggingAccess),
509         DECLARE_NAPI_STATIC_FUNCTION("setServiceWorkerWebSchemeHandler",
510                                      NapiWebviewController::SetServiceWorkerWebSchemeHandler),
511         DECLARE_NAPI_STATIC_FUNCTION("clearServiceWorkerWebSchemeHandler",
512                                      NapiWebviewController::ClearServiceWorkerWebSchemeHandler),
513         DECLARE_NAPI_FUNCTION("getWebDebuggingAccess", NapiWebviewController::InnerGetWebDebuggingAccess),
514         DECLARE_NAPI_FUNCTION("setWebId", NapiWebviewController::SetWebId),
515         DECLARE_NAPI_FUNCTION("jsProxy", NapiWebviewController::InnerJsProxy),
516         DECLARE_NAPI_FUNCTION("getCustomeSchemeCmdLine", NapiWebviewController::InnerGetCustomeSchemeCmdLine),
517         DECLARE_NAPI_FUNCTION("accessForward", NapiWebviewController::AccessForward),
518         DECLARE_NAPI_FUNCTION("accessBackward", NapiWebviewController::AccessBackward),
519         DECLARE_NAPI_FUNCTION("accessStep", NapiWebviewController::AccessStep),
520         DECLARE_NAPI_FUNCTION("clearHistory", NapiWebviewController::ClearHistory),
521         DECLARE_NAPI_FUNCTION("forward", NapiWebviewController::Forward),
522         DECLARE_NAPI_FUNCTION("backward", NapiWebviewController::Backward),
523         DECLARE_NAPI_FUNCTION("onActive", NapiWebviewController::OnActive),
524         DECLARE_NAPI_FUNCTION("onInactive", NapiWebviewController::OnInactive),
525         DECLARE_NAPI_FUNCTION("refresh", NapiWebviewController::Refresh),
526         DECLARE_NAPI_FUNCTION("zoomIn", NapiWebviewController::ZoomIn),
527         DECLARE_NAPI_FUNCTION("zoomOut", NapiWebviewController::ZoomOut),
528         DECLARE_NAPI_FUNCTION("getWebId", NapiWebviewController::GetWebId),
529         DECLARE_NAPI_FUNCTION("getUserAgent", NapiWebviewController::GetUserAgent),
530         DECLARE_NAPI_FUNCTION("getCustomUserAgent", NapiWebviewController::GetCustomUserAgent),
531         DECLARE_NAPI_FUNCTION("setCustomUserAgent", NapiWebviewController::SetCustomUserAgent),
532         DECLARE_NAPI_FUNCTION("getTitle", NapiWebviewController::GetTitle),
533         DECLARE_NAPI_FUNCTION("getPageHeight", NapiWebviewController::GetPageHeight),
534         DECLARE_NAPI_FUNCTION("backOrForward", NapiWebviewController::BackOrForward),
535         DECLARE_NAPI_FUNCTION("storeWebArchive", NapiWebviewController::StoreWebArchive),
536         DECLARE_NAPI_FUNCTION("createWebMessagePorts", NapiWebviewController::CreateWebMessagePorts),
537         DECLARE_NAPI_FUNCTION("postMessage", NapiWebviewController::PostMessage),
538         DECLARE_NAPI_FUNCTION("getHitTestValue", NapiWebviewController::GetHitTestValue),
539         DECLARE_NAPI_FUNCTION("requestFocus", NapiWebviewController::RequestFocus),
540         DECLARE_NAPI_FUNCTION("loadUrl", NapiWebviewController::LoadUrl),
541         DECLARE_NAPI_FUNCTION("postUrl", NapiWebviewController::PostUrl),
542         DECLARE_NAPI_FUNCTION("loadData", NapiWebviewController::LoadData),
543         DECLARE_NAPI_FUNCTION("getHitTest", NapiWebviewController::GetHitTest),
544         DECLARE_NAPI_FUNCTION("clearMatches", NapiWebviewController::ClearMatches),
545         DECLARE_NAPI_FUNCTION("searchNext", NapiWebviewController::SearchNext),
546         DECLARE_NAPI_FUNCTION("searchAllAsync", NapiWebviewController::SearchAllAsync),
547         DECLARE_NAPI_FUNCTION("clearSslCache", NapiWebviewController::ClearSslCache),
548         DECLARE_NAPI_FUNCTION("clearClientAuthenticationCache", NapiWebviewController::ClearClientAuthenticationCache),
549         DECLARE_NAPI_FUNCTION("stop", NapiWebviewController::Stop),
550         DECLARE_NAPI_FUNCTION("zoom", NapiWebviewController::Zoom),
551         DECLARE_NAPI_FUNCTION("registerJavaScriptProxy", NapiWebviewController::RegisterJavaScriptProxy),
552         DECLARE_NAPI_FUNCTION("innerCompleteWindowNew", NapiWebviewController::InnerCompleteWindowNew),
553         DECLARE_NAPI_FUNCTION("deleteJavaScriptRegister", NapiWebviewController::DeleteJavaScriptRegister),
554         DECLARE_NAPI_FUNCTION("runJavaScript", NapiWebviewController::RunJavaScript),
555         DECLARE_NAPI_FUNCTION("runJavaScriptExt", NapiWebviewController::RunJavaScriptExt),
556         DECLARE_NAPI_FUNCTION("getUrl", NapiWebviewController::GetUrl),
557         DECLARE_NAPI_FUNCTION("terminateRenderProcess", NapiWebviewController::TerminateRenderProcess),
558         DECLARE_NAPI_FUNCTION("getOriginalUrl", NapiWebviewController::GetOriginalUrl),
559         DECLARE_NAPI_FUNCTION("setNetworkAvailable", NapiWebviewController::SetNetworkAvailable),
560         DECLARE_NAPI_FUNCTION("innerGetWebId", NapiWebviewController::InnerGetWebId),
561         DECLARE_NAPI_FUNCTION("hasImage", NapiWebviewController::HasImage),
562         DECLARE_NAPI_FUNCTION("removeCache", NapiWebviewController::RemoveCache),
563         DECLARE_NAPI_FUNCTION("getFavicon", NapiWebviewController::GetFavicon),
564         DECLARE_NAPI_FUNCTION("getBackForwardEntries", NapiWebviewController::getBackForwardEntries),
565         DECLARE_NAPI_FUNCTION("serializeWebState", NapiWebviewController::SerializeWebState),
566         DECLARE_NAPI_FUNCTION("restoreWebState", NapiWebviewController::RestoreWebState),
567         DECLARE_NAPI_FUNCTION("pageDown", NapiWebviewController::ScrollPageDown),
568         DECLARE_NAPI_FUNCTION("pageUp", NapiWebviewController::ScrollPageUp),
569         DECLARE_NAPI_FUNCTION("scrollTo", NapiWebviewController::ScrollTo),
570         DECLARE_NAPI_FUNCTION("scrollBy", NapiWebviewController::ScrollBy),
571         DECLARE_NAPI_FUNCTION("slideScroll", NapiWebviewController::SlideScroll),
572         DECLARE_NAPI_FUNCTION("setScrollable", NapiWebviewController::SetScrollable),
573         DECLARE_NAPI_FUNCTION("getScrollable", NapiWebviewController::GetScrollable),
574         DECLARE_NAPI_STATIC_FUNCTION("customizeSchemes", NapiWebviewController::CustomizeSchemes),
575         DECLARE_NAPI_FUNCTION("innerSetHapPath", NapiWebviewController::InnerSetHapPath),
576         DECLARE_NAPI_FUNCTION("innerGetCertificate", NapiWebviewController::InnerGetCertificate),
577         DECLARE_NAPI_FUNCTION("setAudioMuted", NapiWebviewController::SetAudioMuted),
578         DECLARE_NAPI_FUNCTION("innerGetThisVar", NapiWebviewController::InnerGetThisVar),
579         DECLARE_NAPI_FUNCTION("prefetchPage", NapiWebviewController::PrefetchPage),
580         DECLARE_NAPI_FUNCTION("setDownloadDelegate", NapiWebviewController::SetDownloadDelegate),
581         DECLARE_NAPI_FUNCTION("startDownload", NapiWebviewController::StartDownload),
582         DECLARE_NAPI_STATIC_FUNCTION("prepareForPageLoad", NapiWebviewController::PrepareForPageLoad),
583         DECLARE_NAPI_FUNCTION("createWebPrintDocumentAdapter", NapiWebviewController::CreateWebPrintDocumentAdapter),
584         DECLARE_NAPI_STATIC_FUNCTION("setConnectionTimeout", NapiWebviewController::SetConnectionTimeout),
585         DECLARE_NAPI_FUNCTION("enableSafeBrowsing", NapiWebviewController::EnableSafeBrowsing),
586         DECLARE_NAPI_FUNCTION("isSafeBrowsingEnabled", NapiWebviewController::IsSafeBrowsingEnabled),
587         DECLARE_NAPI_FUNCTION("getSecurityLevel", NapiWebviewController::GetSecurityLevel),
588         DECLARE_NAPI_FUNCTION("isIncognitoMode", NapiWebviewController::IsIncognitoMode),
589         DECLARE_NAPI_FUNCTION("setPrintBackground", NapiWebviewController::SetPrintBackground),
590         DECLARE_NAPI_FUNCTION("getPrintBackground", NapiWebviewController::GetPrintBackground),
591         DECLARE_NAPI_FUNCTION("setWebSchemeHandler", NapiWebviewController::SetWebSchemeHandler),
592         DECLARE_NAPI_FUNCTION("clearWebSchemeHandler", NapiWebviewController::ClearWebSchemeHandler),
593         DECLARE_NAPI_FUNCTION("enableIntelligentTrackingPrevention",
594             NapiWebviewController::EnableIntelligentTrackingPrevention),
595         DECLARE_NAPI_FUNCTION("isIntelligentTrackingPreventionEnabled",
596             NapiWebviewController::IsIntelligentTrackingPreventionEnabled),
597         DECLARE_NAPI_STATIC_FUNCTION("addIntelligentTrackingPreventionBypassingList",
598             NapiWebviewController::AddIntelligentTrackingPreventionBypassingList),
599         DECLARE_NAPI_STATIC_FUNCTION("removeIntelligentTrackingPreventionBypassingList",
600             NapiWebviewController::RemoveIntelligentTrackingPreventionBypassingList),
601         DECLARE_NAPI_STATIC_FUNCTION("clearIntelligentTrackingPreventionBypassingList",
602             NapiWebviewController::ClearIntelligentTrackingPreventionBypassingList),
603         DECLARE_NAPI_FUNCTION("getLastJavascriptProxyCallingFrameUrl",
604             NapiWebviewController::GetLastJavascriptProxyCallingFrameUrl),
605         DECLARE_NAPI_STATIC_FUNCTION("getDefaultUserAgent", NapiWebviewController::GetDefaultUserAgent),
606         DECLARE_NAPI_STATIC_FUNCTION("pauseAllTimers", NapiWebviewController::PauseAllTimers),
607         DECLARE_NAPI_STATIC_FUNCTION("resumeAllTimers", NapiWebviewController::ResumeAllTimers),
608         DECLARE_NAPI_FUNCTION("startCamera", NapiWebviewController::StartCamera),
609         DECLARE_NAPI_FUNCTION("stopCamera", NapiWebviewController::StopCamera),
610         DECLARE_NAPI_FUNCTION("closeCamera", NapiWebviewController::CloseCamera),
611         DECLARE_NAPI_FUNCTION("closeAllMediaPresentations", NapiWebviewController::CloseAllMediaPresentations),
612         DECLARE_NAPI_FUNCTION("stopAllMedia", NapiWebviewController::StopAllMedia),
613         DECLARE_NAPI_FUNCTION("resumeAllMedia", NapiWebviewController::ResumeAllMedia),
614         DECLARE_NAPI_FUNCTION("pauseAllMedia", NapiWebviewController::PauseAllMedia),
615         DECLARE_NAPI_FUNCTION("getMediaPlaybackState", NapiWebviewController::GetMediaPlaybackState),
616         DECLARE_NAPI_FUNCTION("onCreateNativeMediaPlayer", NapiWebviewController::OnCreateNativeMediaPlayer),
617         DECLARE_NAPI_STATIC_FUNCTION("prefetchResource", NapiWebviewController::PrefetchResource),
618         DECLARE_NAPI_STATIC_FUNCTION("clearPrefetchedResource", NapiWebviewController::ClearPrefetchedResource),
619         DECLARE_NAPI_STATIC_FUNCTION("setRenderProcessMode", NapiWebviewController::SetRenderProcessMode),
620         DECLARE_NAPI_STATIC_FUNCTION("getRenderProcessMode", NapiWebviewController::GetRenderProcessMode),
621         DECLARE_NAPI_FUNCTION("precompileJavaScript", NapiWebviewController::PrecompileJavaScript),
622         DECLARE_NAPI_FUNCTION("injectOfflineResources", NapiWebviewController::InjectOfflineResources),
623         DECLARE_NAPI_STATIC_FUNCTION("setHostIP", NapiWebviewController::SetHostIP),
624         DECLARE_NAPI_STATIC_FUNCTION("clearHostIP", NapiWebviewController::ClearHostIP),
625         DECLARE_NAPI_STATIC_FUNCTION("warmupServiceWorker", NapiWebviewController::WarmupServiceWorker),
626         DECLARE_NAPI_FUNCTION("getSurfaceId", NapiWebviewController::GetSurfaceId),
627         DECLARE_NAPI_STATIC_FUNCTION("enableWholeWebPageDrawing", NapiWebviewController::EnableWholeWebPageDrawing),
628         DECLARE_NAPI_FUNCTION("enableAdsBlock", NapiWebviewController::EnableAdsBlock),
629         DECLARE_NAPI_FUNCTION("isAdsBlockEnabled", NapiWebviewController::IsAdsBlockEnabled),
630         DECLARE_NAPI_FUNCTION("isAdsBlockEnabledForCurPage", NapiWebviewController::IsAdsBlockEnabledForCurPage),
631         DECLARE_NAPI_FUNCTION("webPageSnapshot", NapiWebviewController::WebPageSnapshot),
632         DECLARE_NAPI_FUNCTION("setUrlTrustList", NapiWebviewController::SetUrlTrustList),
633         DECLARE_NAPI_FUNCTION("setPathAllowingUniversalAccess",
634             NapiWebviewController::SetPathAllowingUniversalAccess),
635         DECLARE_NAPI_STATIC_FUNCTION("enableBackForwardCache", NapiWebviewController::EnableBackForwardCache),
636         DECLARE_NAPI_FUNCTION("setBackForwardCacheOptions", NapiWebviewController::SetBackForwardCacheOptions),
637         DECLARE_NAPI_FUNCTION("scrollByWithResult", NapiWebviewController::ScrollByWithResult),
638         DECLARE_NAPI_FUNCTION("updateInstanceId", NapiWebviewController::UpdateInstanceId),
639         DECLARE_NAPI_STATIC_FUNCTION("trimMemoryByPressureLevel",
640             NapiWebviewController::TrimMemoryByPressureLevel),
641         DECLARE_NAPI_FUNCTION("getScrollOffset",
642             NapiWebviewController::GetScrollOffset),
643         DECLARE_NAPI_FUNCTION("createPdf", NapiWebviewController::RunCreatePDFExt),
644     };
645     napi_value constructor = nullptr;
646     napi_define_class(env, WEBVIEW_CONTROLLER_CLASS_NAME.c_str(), WEBVIEW_CONTROLLER_CLASS_NAME.length(),
647         NapiWebviewController::JsConstructor, nullptr, sizeof(properties) / sizeof(properties[0]),
648         properties, &constructor);
649     NAPI_ASSERT(env, constructor != nullptr, "define js class WebviewController failed");
650     napi_status status = napi_set_named_property(env, exports, "WebviewController", constructor);
651     NAPI_ASSERT(env, status == napi_ok, "set property WebviewController failed");
652 
653     napi_value webMsgTypeEnum = nullptr;
654     napi_property_descriptor webMsgTypeProperties[] = {
655         DECLARE_NAPI_STATIC_PROPERTY("NOT_SUPPORT", NapiParseUtils::ToInt32Value(env,
656             static_cast<int32_t>(WebMessageType::NOTSUPPORT))),
657         DECLARE_NAPI_STATIC_PROPERTY("STRING", NapiParseUtils::ToInt32Value(env,
658             static_cast<int32_t>(WebMessageType::STRING))),
659         DECLARE_NAPI_STATIC_PROPERTY("NUMBER", NapiParseUtils::ToInt32Value(env,
660             static_cast<int32_t>(WebMessageType::NUMBER))),
661         DECLARE_NAPI_STATIC_PROPERTY("BOOLEAN", NapiParseUtils::ToInt32Value(env,
662             static_cast<int32_t>(WebMessageType::BOOLEAN))),
663         DECLARE_NAPI_STATIC_PROPERTY("ARRAY_BUFFER", NapiParseUtils::ToInt32Value(env,
664             static_cast<int32_t>(WebMessageType::ARRAYBUFFER))),
665         DECLARE_NAPI_STATIC_PROPERTY("ARRAY", NapiParseUtils::ToInt32Value(env,
666             static_cast<int32_t>(WebMessageType::ARRAY))),
667         DECLARE_NAPI_STATIC_PROPERTY("ERROR", NapiParseUtils::ToInt32Value(env,
668             static_cast<int32_t>(WebMessageType::ERROR)))
669     };
670     napi_define_class(env, WEB_PORT_MSG_ENUM_NAME.c_str(), WEB_PORT_MSG_ENUM_NAME.length(),
671         NapiParseUtils::CreateEnumConstructor, nullptr, sizeof(webMsgTypeProperties) /
672         sizeof(webMsgTypeProperties[0]), webMsgTypeProperties, &webMsgTypeEnum);
673     napi_set_named_property(env, exports, WEB_PORT_MSG_ENUM_NAME.c_str(), webMsgTypeEnum);
674 
675     napi_value webMsgExtClass = nullptr;
676     napi_property_descriptor webMsgExtClsProperties[] = {
677         DECLARE_NAPI_FUNCTION("getType", NapiWebMessageExt::GetType),
678         DECLARE_NAPI_FUNCTION("getString", NapiWebMessageExt::GetString),
679         DECLARE_NAPI_FUNCTION("getNumber", NapiWebMessageExt::GetNumber),
680         DECLARE_NAPI_FUNCTION("getBoolean", NapiWebMessageExt::GetBoolean),
681         DECLARE_NAPI_FUNCTION("getArrayBuffer", NapiWebMessageExt::GetArrayBuffer),
682         DECLARE_NAPI_FUNCTION("getArray", NapiWebMessageExt::GetArray),
683         DECLARE_NAPI_FUNCTION("getError", NapiWebMessageExt::GetError),
684         DECLARE_NAPI_FUNCTION("setType", NapiWebMessageExt::SetType),
685         DECLARE_NAPI_FUNCTION("setString", NapiWebMessageExt::SetString),
686         DECLARE_NAPI_FUNCTION("setNumber", NapiWebMessageExt::SetNumber),
687         DECLARE_NAPI_FUNCTION("setBoolean", NapiWebMessageExt::SetBoolean),
688         DECLARE_NAPI_FUNCTION("setArrayBuffer", NapiWebMessageExt::SetArrayBuffer),
689         DECLARE_NAPI_FUNCTION("setArray", NapiWebMessageExt::SetArray),
690         DECLARE_NAPI_FUNCTION("setError", NapiWebMessageExt::SetError)
691     };
692     napi_define_class(env, WEB_EXT_MSG_CLASS_NAME.c_str(), WEB_EXT_MSG_CLASS_NAME.length(),
693         NapiWebMessageExt::JsConstructor, nullptr, sizeof(webMsgExtClsProperties) / sizeof(webMsgExtClsProperties[0]),
694         webMsgExtClsProperties, &webMsgExtClass);
695     napi_create_reference(env, webMsgExtClass, 1, &g_webMsgExtClassRef);
696     napi_set_named_property(env, exports, WEB_EXT_MSG_CLASS_NAME.c_str(), webMsgExtClass);
697 
698     napi_value securityLevelEnum = nullptr;
699     napi_property_descriptor securityLevelProperties[] = {
700         DECLARE_NAPI_STATIC_PROPERTY("NONE", NapiParseUtils::ToInt32Value(env,
701             static_cast<int32_t>(SecurityLevel::NONE))),
702         DECLARE_NAPI_STATIC_PROPERTY("SECURE", NapiParseUtils::ToInt32Value(env,
703             static_cast<int32_t>(SecurityLevel::SECURE))),
704         DECLARE_NAPI_STATIC_PROPERTY("WARNING", NapiParseUtils::ToInt32Value(env,
705             static_cast<int32_t>(SecurityLevel::WARNING))),
706         DECLARE_NAPI_STATIC_PROPERTY("DANGEROUS", NapiParseUtils::ToInt32Value(env,
707             static_cast<int32_t>(SecurityLevel::DANGEROUS)))
708     };
709     napi_define_class(env, WEB_SECURITY_LEVEL_ENUM_NAME.c_str(), WEB_SECURITY_LEVEL_ENUM_NAME.length(),
710         NapiParseUtils::CreateEnumConstructor, nullptr, sizeof(securityLevelProperties) /
711         sizeof(securityLevelProperties[0]), securityLevelProperties, &securityLevelEnum);
712     napi_set_named_property(env, exports, WEB_SECURITY_LEVEL_ENUM_NAME.c_str(), securityLevelEnum);
713 
714     napi_value msgPortCons = nullptr;
715     napi_property_descriptor msgPortProperties[] = {
716         DECLARE_NAPI_FUNCTION("close", NapiWebMessagePort::Close),
717         DECLARE_NAPI_FUNCTION("postMessageEvent", NapiWebMessagePort::PostMessageEvent),
718         DECLARE_NAPI_FUNCTION("onMessageEvent", NapiWebMessagePort::OnMessageEvent),
719         DECLARE_NAPI_FUNCTION("postMessageEventExt", NapiWebMessagePort::PostMessageEventExt),
720         DECLARE_NAPI_FUNCTION("onMessageEventExt", NapiWebMessagePort::OnMessageEventExt)
721     };
722     NAPI_CALL(env, napi_define_class(env, WEB_MESSAGE_PORT_CLASS_NAME.c_str(), WEB_MESSAGE_PORT_CLASS_NAME.length(),
723         NapiWebMessagePort::JsConstructor, nullptr, sizeof(msgPortProperties) / sizeof(msgPortProperties[0]),
724         msgPortProperties, &msgPortCons));
725     NAPI_CALL(env, napi_create_reference(env, msgPortCons, 1, &g_classWebMsgPort));
726     NAPI_CALL(env, napi_set_named_property(env, exports, WEB_MESSAGE_PORT_CLASS_NAME.c_str(), msgPortCons));
727 
728     napi_value hitTestTypeEnum = nullptr;
729     napi_property_descriptor hitTestTypeProperties[] = {
730         DECLARE_NAPI_STATIC_PROPERTY("EditText", NapiParseUtils::ToInt32Value(env,
731             static_cast<int32_t>(WebHitTestType::EDIT))),
732         DECLARE_NAPI_STATIC_PROPERTY("Email", NapiParseUtils::ToInt32Value(env,
733             static_cast<int32_t>(WebHitTestType::EMAIL))),
734         DECLARE_NAPI_STATIC_PROPERTY("HttpAnchor", NapiParseUtils::ToInt32Value(env,
735             static_cast<int32_t>(WebHitTestType::HTTP))),
736         DECLARE_NAPI_STATIC_PROPERTY("HttpAnchorImg", NapiParseUtils::ToInt32Value(env,
737             static_cast<int32_t>(WebHitTestType::HTTP_IMG))),
738         DECLARE_NAPI_STATIC_PROPERTY("Img", NapiParseUtils::ToInt32Value(env,
739             static_cast<int32_t>(WebHitTestType::IMG))),
740         DECLARE_NAPI_STATIC_PROPERTY("Map", NapiParseUtils::ToInt32Value(env,
741             static_cast<int32_t>(WebHitTestType::MAP))),
742         DECLARE_NAPI_STATIC_PROPERTY("Phone", NapiParseUtils::ToInt32Value(env,
743             static_cast<int32_t>(WebHitTestType::PHONE))),
744         DECLARE_NAPI_STATIC_PROPERTY("Unknown", NapiParseUtils::ToInt32Value(env,
745             static_cast<int32_t>(WebHitTestType::UNKNOWN))),
746     };
747     napi_define_class(env, WEB_HITTESTTYPE_V9_ENUM_NAME.c_str(), WEB_HITTESTTYPE_V9_ENUM_NAME.length(),
748         NapiParseUtils::CreateEnumConstructor, nullptr, sizeof(hitTestTypeProperties) /
749         sizeof(hitTestTypeProperties[0]), hitTestTypeProperties, &hitTestTypeEnum);
750     napi_set_named_property(env, exports, WEB_HITTESTTYPE_V9_ENUM_NAME.c_str(), hitTestTypeEnum);
751 
752     napi_define_class(env, WEB_HITTESTTYPE_ENUM_NAME.c_str(), WEB_HITTESTTYPE_ENUM_NAME.length(),
753         NapiParseUtils::CreateEnumConstructor, nullptr, sizeof(hitTestTypeProperties) /
754         sizeof(hitTestTypeProperties[0]), hitTestTypeProperties, &hitTestTypeEnum);
755     napi_set_named_property(env, exports, WEB_HITTESTTYPE_ENUM_NAME.c_str(), hitTestTypeEnum);
756 
757     napi_value secureDnsModeEnum = nullptr;
758     napi_property_descriptor secureDnsModeProperties[] = {
759         DECLARE_NAPI_STATIC_PROPERTY("Off", NapiParseUtils::ToInt32Value(env,
760             static_cast<int32_t>(SecureDnsModeType::OFF))),
761         DECLARE_NAPI_STATIC_PROPERTY("Auto", NapiParseUtils::ToInt32Value(env,
762             static_cast<int32_t>(SecureDnsModeType::AUTO))),
763         DECLARE_NAPI_STATIC_PROPERTY("SecureOnly", NapiParseUtils::ToInt32Value(env,
764             static_cast<int32_t>(SecureDnsModeType::SECURE_ONLY))),
765         DECLARE_NAPI_STATIC_PROPERTY("OFF", NapiParseUtils::ToInt32Value(env,
766             static_cast<int32_t>(SecureDnsModeType::OFF))),
767         DECLARE_NAPI_STATIC_PROPERTY("AUTO", NapiParseUtils::ToInt32Value(env,
768             static_cast<int32_t>(SecureDnsModeType::AUTO))),
769         DECLARE_NAPI_STATIC_PROPERTY("SECURE_ONLY", NapiParseUtils::ToInt32Value(env,
770             static_cast<int32_t>(SecureDnsModeType::SECURE_ONLY))),
771     };
772     napi_define_class(env, WEB_SECURE_DNS_MODE_ENUM_NAME.c_str(), WEB_SECURE_DNS_MODE_ENUM_NAME.length(),
773         NapiParseUtils::CreateEnumConstructor, nullptr, sizeof(secureDnsModeProperties) /
774         sizeof(secureDnsModeProperties[0]), secureDnsModeProperties, &secureDnsModeEnum);
775     napi_set_named_property(env, exports, WEB_SECURE_DNS_MODE_ENUM_NAME.c_str(), secureDnsModeEnum);
776 
777     napi_value historyList = nullptr;
778     napi_property_descriptor historyListProperties[] = {
779         DECLARE_NAPI_FUNCTION("getItemAtIndex", NapiWebHistoryList::GetItem)
780     };
781     napi_define_class(env, WEB_HISTORY_LIST_CLASS_NAME.c_str(), WEB_HISTORY_LIST_CLASS_NAME.length(),
782         NapiWebHistoryList::JsConstructor, nullptr, sizeof(historyListProperties) / sizeof(historyListProperties[0]),
783         historyListProperties, &historyList);
784     napi_create_reference(env, historyList, 1, &g_historyListRef);
785     napi_set_named_property(env, exports, WEB_HISTORY_LIST_CLASS_NAME.c_str(), historyList);
786 
787     napi_value webPrintDoc = nullptr;
788     napi_property_descriptor WebPrintDocumentClass[] = {
789         DECLARE_NAPI_FUNCTION("onStartLayoutWrite", NapiWebPrintDocument::OnStartLayoutWrite),
790         DECLARE_NAPI_FUNCTION("onJobStateChanged", NapiWebPrintDocument::OnJobStateChanged),
791     };
792     napi_define_class(env, WEB_PRINT_DOCUMENT_CLASS_NAME.c_str(), WEB_PRINT_DOCUMENT_CLASS_NAME.length(),
793         NapiWebPrintDocument::JsConstructor, nullptr,
794         sizeof(WebPrintDocumentClass) / sizeof(WebPrintDocumentClass[0]),
795         WebPrintDocumentClass, &webPrintDoc);
796     napi_create_reference(env, webPrintDoc, 1, &g_webPrintDocClassRef);
797     napi_set_named_property(env, exports, WEB_PRINT_DOCUMENT_CLASS_NAME.c_str(), webPrintDoc);
798 
799     napi_value renderProcessModeEnum = nullptr;
800     napi_property_descriptor renderProcessModeProperties[] = {
801         DECLARE_NAPI_STATIC_PROPERTY("SINGLE", NapiParseUtils::ToInt32Value(env,
802             static_cast<int32_t>(RenderProcessMode::SINGLE_MODE))),
803         DECLARE_NAPI_STATIC_PROPERTY("MULTIPLE", NapiParseUtils::ToInt32Value(env,
804             static_cast<int32_t>(RenderProcessMode::MULTIPLE_MODE))),
805     };
806     napi_define_class(env, WEB_RENDER_PROCESS_MODE_ENUM_NAME.c_str(), WEB_RENDER_PROCESS_MODE_ENUM_NAME.length(),
807         NapiParseUtils::CreateEnumConstructor, nullptr, sizeof(renderProcessModeProperties) /
808         sizeof(renderProcessModeProperties[0]), renderProcessModeProperties, &renderProcessModeEnum);
809     napi_set_named_property(env, exports, WEB_RENDER_PROCESS_MODE_ENUM_NAME.c_str(), renderProcessModeEnum);
810 
811     napi_value offlineResourceTypeEnum = nullptr;
812     napi_property_descriptor offlineResourceTypeProperties[] = {
813         DECLARE_NAPI_STATIC_PROPERTY("IMAGE", NapiParseUtils::ToInt32Value(env,
814             static_cast<int32_t>(OfflineResourceType::IMAGE))),
815         DECLARE_NAPI_STATIC_PROPERTY("CSS", NapiParseUtils::ToInt32Value(env,
816             static_cast<int32_t>(OfflineResourceType::CSS))),
817         DECLARE_NAPI_STATIC_PROPERTY("CLASSIC_JS", NapiParseUtils::ToInt32Value(env,
818             static_cast<int32_t>(OfflineResourceType::CLASSIC_JS))),
819         DECLARE_NAPI_STATIC_PROPERTY("MODULE_JS", NapiParseUtils::ToInt32Value(env,
820             static_cast<int32_t>(OfflineResourceType::MODULE_JS))),
821     };
822     napi_define_class(env, OFFLINE_RESOURCE_TYPE_ENUM_NAME.c_str(), OFFLINE_RESOURCE_TYPE_ENUM_NAME.length(),
823         NapiParseUtils::CreateEnumConstructor, nullptr, sizeof(offlineResourceTypeProperties) /
824         sizeof(offlineResourceTypeProperties[0]), offlineResourceTypeProperties, &offlineResourceTypeEnum);
825     napi_set_named_property(env, exports, OFFLINE_RESOURCE_TYPE_ENUM_NAME.c_str(), offlineResourceTypeEnum);
826 
827     napi_value pressureLevelEnum = nullptr;
828     napi_property_descriptor pressureLevelProperties[] = {
829         DECLARE_NAPI_STATIC_PROPERTY("MEMORY_PRESSURE_LEVEL_MODERATE", NapiParseUtils::ToInt32Value(env,
830             static_cast<int32_t>(PressureLevel::MEMORY_PRESSURE_LEVEL_MODERATE))),
831         DECLARE_NAPI_STATIC_PROPERTY("MEMORY_PRESSURE_LEVEL_CRITICAL", NapiParseUtils::ToInt32Value(env,
832             static_cast<int32_t>(PressureLevel::MEMORY_PRESSURE_LEVEL_CRITICAL))),
833     };
834     napi_define_class(env, WEB_PRESSURE_LEVEL_ENUM_NAME.c_str(), WEB_PRESSURE_LEVEL_ENUM_NAME.length(),
835         NapiParseUtils::CreateEnumConstructor, nullptr, sizeof(pressureLevelProperties) /
836         sizeof(pressureLevelProperties[0]), pressureLevelProperties, &pressureLevelEnum);
837     napi_set_named_property(env, exports, WEB_PRESSURE_LEVEL_ENUM_NAME.c_str(), pressureLevelEnum);
838 
839     napi_value scrollTypeEnum = nullptr;
840     napi_property_descriptor scrollTypeProperties[] = {
841         DECLARE_NAPI_STATIC_PROPERTY("EVENT", NapiParseUtils::ToInt32Value(env,
842             static_cast<int32_t>(ScrollType::EVENT))),
843     };
844     napi_define_class(env, WEB_SCROLL_TYPE_ENUM_NAME.c_str(), WEB_SCROLL_TYPE_ENUM_NAME.length(),
845         NapiParseUtils::CreateEnumConstructor, nullptr, sizeof(scrollTypeProperties) /
846         sizeof(scrollTypeProperties[0]), scrollTypeProperties, &scrollTypeEnum);
847     napi_set_named_property(env, exports, WEB_SCROLL_TYPE_ENUM_NAME.c_str(), scrollTypeEnum);
848 
849     WebviewJavaScriptExecuteCallback::InitJSExcute(env, exports);
850     WebviewCreatePDFExecuteCallback::InitJSExcute(env, exports);
851     return exports;
852 }
853 
JsConstructor(napi_env env, napi_callback_info info)854 napi_value NapiWebviewController::JsConstructor(napi_env env, napi_callback_info info)
855 {
856     WVLOG_I("NapiWebviewController::JsConstructor start");
857     napi_value thisVar = nullptr;
858 
859     size_t argc = INTEGER_ONE;
860     napi_value argv[INTEGER_ONE] = { 0 };
861     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
862 
863     WebviewController *webviewController;
864     std::string webTag;
865     if (argc == 1) {
866         NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], webTag);
867         if (webTag.empty()) {
868             WVLOG_E("native webTag is empty");
869             return nullptr;
870         }
871         webviewController = new (std::nothrow) WebviewController(webTag);
872         WVLOG_I("new webview controller webname:%{public}s", webTag.c_str());
873     } else {
874         webTag = WebviewController::GenerateWebTag();
875         webviewController = new (std::nothrow) WebviewController(webTag);
876     }
877     WebviewController::webTagSet_.insert(webTag);
878 
879     if (webviewController == nullptr) {
880         WVLOG_E("new webview controller failed");
881         return nullptr;
882     }
883     napi_status status = napi_wrap(
884         env, thisVar, webviewController,
885         [](napi_env env, void *data, void *hint) {
886             WebviewController *webviewController = static_cast<WebviewController *>(data);
887             delete webviewController;
888         },
889         nullptr, nullptr);
890     if (status != napi_ok) {
891         WVLOG_E("Wrap native webviewController failed.");
892         return nullptr;
893     }
894     return thisVar;
895 }
896 
InitializeWebEngine(napi_env env, napi_callback_info info)897 napi_value NapiWebviewController::InitializeWebEngine(napi_env env, napi_callback_info info)
898 {
899     WVLOG_D("InitializeWebEngine invoked.");
900 
901     // obtain bundle path
902     std::shared_ptr<AbilityRuntime::ApplicationContext> ctx =
903         AbilityRuntime::ApplicationContext::GetApplicationContext();
904     if (!ctx) {
905         WVLOG_E("Failed to init web engine due to nil application context.");
906         return nullptr;
907     }
908 
909     // load so
910     const std::string& bundlePath = ctx->GetBundleCodeDir();
911     NWebHelper::Instance().SetBundlePath(bundlePath);
912     if (!NWebHelper::Instance().InitAndRun(true)) {
913         WVLOG_E("Failed to init web engine due to NWebHelper failure.");
914         return nullptr;
915     }
916 
917     napi_value result = nullptr;
918     NAPI_CALL(env, napi_get_undefined(env, &result));
919     WVLOG_I("NWebHelper initialized, init web engine done, bundle_path: %{public}s", bundlePath.c_str());
920     return result;
921 }
922 
SetHttpDns(napi_env env, napi_callback_info info)923 napi_value NapiWebviewController::SetHttpDns(napi_env env, napi_callback_info info)
924 {
925     napi_value thisVar = nullptr;
926     napi_value result = nullptr;
927     size_t argc = INTEGER_TWO;
928     napi_value argv[INTEGER_TWO] = { 0 };
929     int dohMode;
930     std::string dohConfig;
931 
932     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
933     if (argc != INTEGER_TWO) {
934         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
935             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "two"));
936         return result;
937     }
938 
939     if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_ZERO], dohMode)) {
940         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
941             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "secureDnsMode", "SecureDnsMode"));
942         return result;
943     }
944 
945     if (dohMode < static_cast<int>(SecureDnsModeType::OFF) ||
946         dohMode > static_cast<int>(SecureDnsModeType::SECURE_ONLY)) {
947         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
948             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "secureDnsMode"));
949         return result;
950     }
951 
952     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ONE], dohConfig)) {
953         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
954             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "secureDnsConfig", "string"));
955         return result;
956     }
957 
958     if (dohConfig.rfind("https", 0) != 0 && dohConfig.rfind("HTTPS", 0) != 0) {
959         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
960             "BusinessError 401: Parameter error. Parameter secureDnsConfig must start with 'http' or 'https'.");
961         return result;
962     }
963 
964     std::shared_ptr<NWebDOHConfigImpl> config = std::make_shared<NWebDOHConfigImpl>();
965     config->SetMode(dohMode);
966     config->SetConfig(dohConfig);
967     WVLOG_I("set http dns mode:%{public}d doh_config:%{public}s", dohMode, dohConfig.c_str());
968 
969     NWebHelper::Instance().SetHttpDns(config);
970 
971     NAPI_CALL(env, napi_get_undefined(env, &result));
972     return result;
973 }
974 
SetWebDebuggingAccess(napi_env env, napi_callback_info info)975 napi_value NapiWebviewController::SetWebDebuggingAccess(napi_env env, napi_callback_info info)
976 {
977     WVLOG_D("SetWebDebuggingAccess start");
978     napi_value result = nullptr;
979     if (OHOS::system::GetBoolParameter("web.debug.devtools", false)) {
980         return result;
981     }
982     napi_value thisVar = nullptr;
983     size_t argc = INTEGER_ONE;
984     napi_value argv[INTEGER_ONE] = {0};
985 
986     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
987     if (argc != INTEGER_ONE) {
988         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
989             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
990         return result;
991     }
992 
993     bool webDebuggingAccess = false;
994     if (!NapiParseUtils::ParseBoolean(env, argv[0], webDebuggingAccess)) {
995         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
996             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "webDebuggingAccess", "boolean"));
997         return result;
998     }
999     WebviewController::webDebuggingAccess_ = webDebuggingAccess;
1000 
1001     NAPI_CALL(env, napi_get_undefined(env, &result));
1002     return result;
1003 }
1004 
EnableSafeBrowsing(napi_env env, napi_callback_info info)1005 napi_value NapiWebviewController::EnableSafeBrowsing(napi_env env, napi_callback_info info)
1006 {
1007     WVLOG_D("EnableSafeBrowsing start");
1008     napi_value result = nullptr;
1009     napi_value thisVar = nullptr;
1010     size_t argc = INTEGER_ONE;
1011     napi_value argv[INTEGER_ONE] = {0};
1012 
1013     NAPI_CALL(env, napi_get_undefined(env, &result));
1014     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
1015     if (argc != INTEGER_ONE) {
1016         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1017             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
1018         return result;
1019     }
1020 
1021     bool safeBrowsingEnable = false;
1022     if (!NapiParseUtils::ParseBoolean(env, argv[0], safeBrowsingEnable)) {
1023         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1024             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "enable", "boolean"));
1025         return result;
1026     }
1027 
1028     WebviewController *controller = nullptr;
1029     napi_unwrap(env, thisVar, (void **)&controller);
1030     if (!controller) {
1031         return result;
1032     }
1033     if (!controller->IsInit()) {
1034         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
1035         return result;
1036     }
1037     controller->EnableSafeBrowsing(safeBrowsingEnable);
1038     return result;
1039 }
1040 
IsSafeBrowsingEnabled(napi_env env, napi_callback_info info)1041 napi_value NapiWebviewController::IsSafeBrowsingEnabled(napi_env env, napi_callback_info info)
1042 {
1043     WVLOG_D("IsSafeBrowsingEnabled start");
1044     napi_value result = nullptr;
1045     WebviewController *webviewController = GetWebviewController(env, info);
1046     if (!webviewController) {
1047         return nullptr;
1048     }
1049 
1050     bool isSafeBrowsingEnabled = webviewController->IsSafeBrowsingEnabled();
1051     NAPI_CALL(env, napi_get_boolean(env, isSafeBrowsingEnabled, &result));
1052     return result;
1053 }
1054 
InnerGetWebDebuggingAccess(napi_env env, napi_callback_info info)1055 napi_value NapiWebviewController::InnerGetWebDebuggingAccess(napi_env env, napi_callback_info info)
1056 {
1057     WVLOG_D("InnerGetWebDebuggingAccess start");
1058     bool webDebuggingAccess = WebviewController::webDebuggingAccess_;
1059     napi_value result = nullptr;
1060     napi_get_boolean(env, webDebuggingAccess, &result);
1061     return result;
1062 }
1063 
InnerGetThisVar(napi_env env, napi_callback_info info)1064 napi_value NapiWebviewController::InnerGetThisVar(napi_env env, napi_callback_info info)
1065 {
1066     WVLOG_D("InnerGetThisVar start");
1067     napi_value thisVar = nullptr;
1068     napi_value result = nullptr;
1069     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
1070     WebviewController *webviewController = nullptr;
1071     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
1072     if ((!webviewController) || (status != napi_ok)) {
1073         WVLOG_E("webviewController is nullptr.");
1074         napi_create_int64(env, 0, &result);
1075     } else {
1076         napi_create_int64(env, reinterpret_cast<int64_t>(webviewController), &result);
1077     }
1078     return result;
1079 }
1080 
SetWebId(napi_env env, napi_callback_info info)1081 napi_value NapiWebviewController::SetWebId(napi_env env, napi_callback_info info)
1082 {
1083     napi_value thisVar = nullptr;
1084     size_t argc = INTEGER_ONE;
1085     napi_value argv[INTEGER_ONE];
1086     void* data = nullptr;
1087     napi_get_cb_info(env, info, &argc, argv, &thisVar, &data);
1088 
1089     int32_t webId = -1;
1090     if (!NapiParseUtils::ParseInt32(env, argv[0], webId)) {
1091         WVLOG_E("Parse web id failed.");
1092         return nullptr;
1093     }
1094     WebviewController *webviewController = nullptr;
1095     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
1096     if ((!webviewController) || (status != napi_ok)) {
1097         WVLOG_E("webviewController is nullptr.");
1098         return nullptr;
1099     }
1100     webviewController->SetWebId(webId);
1101     return thisVar;
1102 }
1103 
InnerSetHapPath(napi_env env, napi_callback_info info)1104 napi_value NapiWebviewController::InnerSetHapPath(napi_env env, napi_callback_info info)
1105 {
1106     napi_value result = nullptr;
1107     NAPI_CALL(env, napi_get_undefined(env, &result));
1108     napi_value thisVar = nullptr;
1109     size_t argc = INTEGER_ONE;
1110     napi_value argv[INTEGER_ONE];
1111     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
1112     if (argc != INTEGER_ONE) {
1113         WVLOG_E("Failed to run InnerSetHapPath beacuse of wrong Param number.");
1114         return result;
1115     }
1116     std::string hapPath;
1117     if (!NapiParseUtils::ParseString(env, argv[0], hapPath)) {
1118         WVLOG_E("Parse hap path failed.");
1119         return result;
1120     }
1121     WebviewController *webviewController = nullptr;
1122     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
1123     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
1124         WVLOG_E("Wrap webviewController failed. WebviewController must be associated with a Web component.");
1125         return result;
1126     }
1127     webviewController->InnerSetHapPath(hapPath);
1128     return result;
1129 }
1130 
InnerJsProxy(napi_env env, napi_callback_info info)1131 napi_value NapiWebviewController::InnerJsProxy(napi_env env, napi_callback_info info)
1132 {
1133     napi_value thisVar = nullptr;
1134     napi_value result = nullptr;
1135     size_t argc = INTEGER_FIVE;
1136     napi_value argv[INTEGER_FIVE] = { 0 };
1137     napi_get_undefined(env, &result);
1138     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
1139     if (argc != INTEGER_FIVE) {
1140         WVLOG_E("Failed to run InnerJsProxy beacuse of wrong Param number.");
1141         return result;
1142     }
1143     napi_valuetype valueType = napi_undefined;
1144     napi_typeof(env, argv[INTEGER_ZERO], &valueType);
1145     if (valueType != napi_object) {
1146         WVLOG_E("Failed to run InnerJsProxy beacuse of wrong Param type.");
1147         return result;
1148     }
1149     std::string objName;
1150     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ONE], objName)) {
1151         WVLOG_E("Failed to run InnerJsProxy beacuse of wrong object name.");
1152         return result;
1153     }
1154     std::vector<std::string> methodList;
1155     bool hasSyncMethod = NapiParseUtils::ParseStringArray(env, argv[INTEGER_TWO], methodList);
1156     std::vector<std::string> asyncMethodList;
1157     bool hasAsyncMethod = NapiParseUtils::ParseStringArray(env, argv[INTEGER_THREE], asyncMethodList);
1158     if (!hasSyncMethod && !hasAsyncMethod) {
1159         WVLOG_E("Failed to run InnerJsProxy beacuse of empty method lists.");
1160         return result;
1161     }
1162     std::string permission = "";
1163     NapiParseUtils::ParseString(env, argv[INTEGER_FOUR], permission);
1164     WebviewController* controller = nullptr;
1165     napi_unwrap(env, thisVar, (void **)&controller);
1166     if (!controller || !controller->IsInit()) {
1167         WVLOG_E("Failed to run InnerJsProxy. The WebviewController must be associted with a Web component.");
1168         return result;
1169     }
1170     controller->SetNWebJavaScriptResultCallBack();
1171     RegisterJavaScriptProxyParam param;
1172     param.env = env;
1173     param.obj = argv[INTEGER_ZERO];
1174     param.objName = objName;
1175     param.syncMethodList = methodList;
1176     param.asyncMethodList = asyncMethodList;
1177     param.permission = permission;
1178     controller->RegisterJavaScriptProxy(param);
1179     return result;
1180 }
1181 
InnerGetCustomeSchemeCmdLine(napi_env env, napi_callback_info info)1182 napi_value NapiWebviewController::InnerGetCustomeSchemeCmdLine(napi_env env, napi_callback_info info)
1183 {
1184     WebviewController::existNweb_ = true;
1185     napi_value result = nullptr;
1186     const std::string& cmdLine = WebviewController::customeSchemeCmdLine_;
1187     napi_create_string_utf8(env, cmdLine.c_str(), cmdLine.length(), &result);
1188     return result;
1189 }
1190 
AccessForward(napi_env env, napi_callback_info info)1191 napi_value NapiWebviewController::AccessForward(napi_env env, napi_callback_info info)
1192 {
1193     napi_value result = nullptr;
1194     WebviewController *webviewController = GetWebviewController(env, info);
1195     if (!webviewController) {
1196         return nullptr;
1197     }
1198 
1199     bool access = webviewController->AccessForward();
1200     NAPI_CALL(env, napi_get_boolean(env, access, &result));
1201     return result;
1202 }
1203 
AccessBackward(napi_env env, napi_callback_info info)1204 napi_value NapiWebviewController::AccessBackward(napi_env env, napi_callback_info info)
1205 {
1206     napi_value result = nullptr;
1207     WebviewController *webviewController = GetWebviewController(env, info);
1208     if (!webviewController) {
1209         return nullptr;
1210     }
1211 
1212     bool access = webviewController->AccessBackward();
1213     NAPI_CALL(env, napi_get_boolean(env, access, &result));
1214     return result;
1215 }
1216 
Forward(napi_env env, napi_callback_info info)1217 napi_value NapiWebviewController::Forward(napi_env env, napi_callback_info info)
1218 {
1219     napi_value result = nullptr;
1220     WebviewController *webviewController = GetWebviewController(env, info);
1221     if (!webviewController) {
1222         return nullptr;
1223     }
1224 
1225     webviewController->Forward();
1226     NAPI_CALL(env, napi_get_undefined(env, &result));
1227     return result;
1228 }
1229 
Backward(napi_env env, napi_callback_info info)1230 napi_value NapiWebviewController::Backward(napi_env env, napi_callback_info info)
1231 {
1232     napi_value result = nullptr;
1233     WebviewController *webviewController = GetWebviewController(env, info);
1234     if (!webviewController) {
1235         return nullptr;
1236     }
1237 
1238     webviewController->Backward();
1239     NAPI_CALL(env, napi_get_undefined(env, &result));
1240     return result;
1241 }
1242 
AccessStep(napi_env env, napi_callback_info info)1243 napi_value NapiWebviewController::AccessStep(napi_env env, napi_callback_info info)
1244 {
1245     napi_value thisVar = nullptr;
1246     napi_value result = nullptr;
1247     size_t argc = INTEGER_ONE;
1248     napi_value argv[INTEGER_ONE];
1249     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
1250     if (argc != INTEGER_ONE) {
1251         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1252             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
1253         return nullptr;
1254     }
1255 
1256     int32_t step = INTEGER_ZERO;
1257     if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_ZERO], step)) {
1258         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1259             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "step", "number"));
1260         return nullptr;
1261     }
1262 
1263     WebviewController *webviewController = nullptr;
1264     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
1265     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
1266         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
1267         return nullptr;
1268     }
1269 
1270     bool access = webviewController->AccessStep(step);
1271     NAPI_CALL(env, napi_get_boolean(env, access, &result));
1272     return result;
1273 }
1274 
ClearHistory(napi_env env, napi_callback_info info)1275 napi_value NapiWebviewController::ClearHistory(napi_env env, napi_callback_info info)
1276 {
1277     napi_value result = nullptr;
1278     WebviewController *webviewController = GetWebviewController(env, info);
1279     if (!webviewController) {
1280         return nullptr;
1281     }
1282 
1283     webviewController->ClearHistory();
1284     NAPI_CALL(env, napi_get_undefined(env, &result));
1285     return result;
1286 }
1287 
OnActive(napi_env env, napi_callback_info info)1288 napi_value NapiWebviewController::OnActive(napi_env env, napi_callback_info info)
1289 {
1290     napi_value result = nullptr;
1291     WebviewController *webviewController = GetWebviewController(env, info);
1292     if (!webviewController) {
1293         WVLOG_E("NapiWebviewController::OnActive get controller failed");
1294         return nullptr;
1295     }
1296 
1297     webviewController->OnActive();
1298     WVLOG_I("The web component has been successfully activated");
1299     NAPI_CALL(env, napi_get_undefined(env, &result));
1300     return result;
1301 }
1302 
OnInactive(napi_env env, napi_callback_info info)1303 napi_value NapiWebviewController::OnInactive(napi_env env, napi_callback_info info)
1304 {
1305     napi_value result = nullptr;
1306     WebviewController *webviewController = GetWebviewController(env, info);
1307     if (!webviewController) {
1308         WVLOG_E("NapiWebviewController::OnInactive get controller failed");
1309         return nullptr;
1310     }
1311 
1312     webviewController->OnInactive();
1313     WVLOG_I("The web component has been successfully inactivated");
1314     NAPI_CALL(env, napi_get_undefined(env, &result));
1315     return result;
1316 }
1317 
Refresh(napi_env env, napi_callback_info info)1318 napi_value NapiWebviewController::Refresh(napi_env env, napi_callback_info info)
1319 {
1320     napi_value result = nullptr;
1321     WebviewController *webviewController = GetWebviewController(env, info);
1322     if (!webviewController) {
1323         return nullptr;
1324     }
1325 
1326     webviewController->Refresh();
1327     NAPI_CALL(env, napi_get_undefined(env, &result));
1328     return result;
1329 }
1330 
1331 
JsConstructor(napi_env env, napi_callback_info info)1332 napi_value NapiWebMessageExt::JsConstructor(napi_env env, napi_callback_info info)
1333 {
1334     WVLOG_D("NapiWebMessageExt::JsConstructor");
1335     napi_value thisVar = nullptr;
1336     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
1337 
1338     auto webMsg = std::make_shared<OHOS::NWeb::NWebMessage>(NWebValue::Type::NONE);
1339     WebMessageExt *webMessageExt = new (std::nothrow) WebMessageExt(webMsg);
1340     if (webMessageExt == nullptr) {
1341         WVLOG_E("new msg port failed");
1342         return nullptr;
1343     }
1344     NAPI_CALL(env, napi_wrap(env, thisVar, webMessageExt,
1345         [](napi_env env, void *data, void *hint) {
1346             WebMessageExt *webMessageExt = static_cast<WebMessageExt *>(data);
1347             if (webMessageExt) {
1348                 delete webMessageExt;
1349             }
1350         },
1351         nullptr, nullptr));
1352     return thisVar;
1353 }
1354 
GetType(napi_env env, napi_callback_info info)1355 napi_value NapiWebMessageExt::GetType(napi_env env, napi_callback_info info)
1356 {
1357     WVLOG_D("NapiWebMessageExt::GetType start");
1358     napi_value thisVar = nullptr;
1359     napi_value result = nullptr;
1360     napi_status status = napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
1361     if (status != napi_status::napi_ok) {
1362         WVLOG_E("napi_get_cb_info status not ok");
1363         return result;
1364     }
1365 
1366     if (thisVar == nullptr) {
1367         WVLOG_E("napi_get_cb_info thisVar is nullptr");
1368         return result;
1369     }
1370 
1371     WebMessageExt *webMessageExt = nullptr;
1372     status = napi_unwrap(env, thisVar, (void **)&webMessageExt);
1373     if ((!webMessageExt) || (status != napi_ok)) {
1374         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
1375         return nullptr;
1376     }
1377 
1378     int32_t type = webMessageExt->GetType();
1379     status = napi_create_int32(env, type, &result);
1380     if (status != napi_status::napi_ok) {
1381         WVLOG_E("napi_create_int32 failed.");
1382         return result;
1383     }
1384     return result;
1385 }
1386 
GetString(napi_env env, napi_callback_info info)1387 napi_value NapiWebMessageExt::GetString(napi_env env, napi_callback_info info)
1388 {
1389     WVLOG_D(" GetString webJsMessageExt start");
1390     napi_value thisVar = nullptr;
1391     napi_value result = nullptr;
1392     size_t argc = INTEGER_ONE;
1393     napi_value argv[INTEGER_ONE] = { 0 };
1394 
1395     WebMessageExt *webJsMessageExt = nullptr;
1396     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
1397     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webJsMessageExt));
1398     if (webJsMessageExt == nullptr) {
1399         WVLOG_E("unwrap webJsMessageExt failed.");
1400         return result;
1401     }
1402 
1403     if (webJsMessageExt->GetType() != static_cast<int32_t>(WebMessageType::STRING)) {
1404         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1405         return nullptr;
1406     }
1407 
1408     NapiParseUtils::ConvertNWebToNapiValue(env, webJsMessageExt->GetData(), result);
1409     return result;
1410 }
1411 
GetNumber(napi_env env, napi_callback_info info)1412 napi_value NapiWebMessageExt::GetNumber(napi_env env, napi_callback_info info)
1413 {
1414     WVLOG_D("GetNumber webJsMessageExt start");
1415     napi_value thisVar = nullptr;
1416     napi_value result = nullptr;
1417     size_t argc = INTEGER_ONE;
1418     napi_value argv[INTEGER_ONE] = { 0 };
1419 
1420     WebMessageExt *webJsMessageExt = nullptr;
1421     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
1422     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webJsMessageExt));
1423     if (webJsMessageExt == nullptr) {
1424         WVLOG_E("unwrap webJsMessageExt failed.");
1425         return result;
1426     }
1427 
1428     if (webJsMessageExt->GetType() != static_cast<int32_t>(WebMessageType::NUMBER)) {
1429         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1430         WVLOG_E("GetNumber webJsMessageExt failed,not match");
1431         return nullptr;
1432     }
1433 
1434     NapiParseUtils::ConvertNWebToNapiValue(env, webJsMessageExt->GetData(), result);
1435     return result;
1436 }
1437 
GetBoolean(napi_env env, napi_callback_info info)1438 napi_value NapiWebMessageExt::GetBoolean(napi_env env, napi_callback_info info)
1439 {
1440     napi_value thisVar = nullptr;
1441     napi_value result = nullptr;
1442     size_t argc = INTEGER_ONE;
1443     napi_value argv[INTEGER_ONE] = { 0 };
1444 
1445     WebMessageExt *webJsMessageExt = nullptr;
1446     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
1447     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webJsMessageExt));
1448     if (webJsMessageExt == nullptr) {
1449         WVLOG_E("unwrap webJsMessageExt failed.");
1450         return result;
1451     }
1452 
1453     if (webJsMessageExt->GetType() != static_cast<int32_t>(WebMessageType::BOOLEAN)) {
1454         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1455         return nullptr;
1456     }
1457 
1458     NapiParseUtils::ConvertNWebToNapiValue(env, webJsMessageExt->GetData(), result);
1459     return result;
1460 }
1461 
GetArrayBuffer(napi_env env, napi_callback_info info)1462 napi_value NapiWebMessageExt::GetArrayBuffer(napi_env env, napi_callback_info info)
1463 {
1464     napi_value thisVar = nullptr;
1465     napi_value result = nullptr;
1466     size_t argc = INTEGER_ONE;
1467     napi_value argv[INTEGER_ONE] = { 0 };
1468 
1469     WebMessageExt *webJsMessageExt = nullptr;
1470     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
1471     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webJsMessageExt));
1472     if (webJsMessageExt == nullptr) {
1473         WVLOG_E("unwrap webJsMessageExt failed.");
1474         return result;
1475     }
1476 
1477     if (webJsMessageExt->GetType() != static_cast<int32_t>(WebMessageType::ARRAYBUFFER)) {
1478         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1479         return nullptr;
1480     }
1481     NapiParseUtils::ConvertNWebToNapiValue(env, webJsMessageExt->GetData(), result);
1482     return result;
1483 }
1484 
GetArray(napi_env env, napi_callback_info info)1485 napi_value NapiWebMessageExt::GetArray(napi_env env, napi_callback_info info)
1486 {
1487     napi_value thisVar = nullptr;
1488     napi_value result = nullptr;
1489     size_t argc = INTEGER_ONE;
1490     napi_value argv[INTEGER_ONE] = { 0 };
1491 
1492     WebMessageExt *webJsMessageExt = nullptr;
1493     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
1494     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webJsMessageExt));
1495     if (webJsMessageExt == nullptr) {
1496         WVLOG_E("unwrap webJsMessageExt failed.");
1497         return result;
1498     }
1499 
1500     if (webJsMessageExt->GetType() != static_cast<int32_t>(WebMessageType::ARRAY)) {
1501         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1502         return nullptr;
1503     }
1504 
1505     NapiParseUtils::ConvertNWebToNapiValue(env, webJsMessageExt->GetData(), result);
1506     return result;
1507 }
1508 
GetError(napi_env env, napi_callback_info info)1509 napi_value NapiWebMessageExt::GetError(napi_env env, napi_callback_info info)
1510 {
1511     napi_value thisVar = nullptr;
1512     napi_value result = nullptr;
1513     size_t argc = INTEGER_ONE;
1514     napi_value argv[INTEGER_ONE] = { 0 };
1515 
1516     WebMessageExt *webJsMessageExt = nullptr;
1517     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
1518     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webJsMessageExt));
1519     if (webJsMessageExt == nullptr) {
1520         WVLOG_E("unwrap webJsMessageExt failed.");
1521         return result;
1522     }
1523 
1524     if (webJsMessageExt->GetType() != static_cast<int32_t>(WebMessageType::ERROR)) {
1525         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1526         return nullptr;
1527     }
1528 
1529     NapiParseUtils::ConvertNWebToNapiValue(env, webJsMessageExt->GetData(), result);
1530     return result;
1531 }
1532 
SetType(napi_env env, napi_callback_info info)1533 napi_value NapiWebMessageExt::SetType(napi_env env, napi_callback_info info)
1534 {
1535     WVLOG_D("NapiWebMessageExt::SetType");
1536     napi_value thisVar = nullptr;
1537     napi_value result = nullptr;
1538     size_t argc = INTEGER_ONE;
1539     napi_value argv[INTEGER_ONE] = { 0 };
1540     int type = -1;
1541     napi_status status = napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
1542     if (status != napi_ok) {
1543         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1544             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "type"));
1545         WVLOG_E("NapiWebMessageExt::SetType napi_get_cb_info failed");
1546         return result;
1547     }
1548     if (thisVar == nullptr) {
1549         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1550             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NOT_NULL, "type"));
1551         WVLOG_E("NapiWebMessageExt::SetType thisVar is null");
1552         return result;
1553     }
1554     if (argc != INTEGER_ONE) {
1555         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1556             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
1557         return result;
1558     }
1559     if (!NapiParseUtils::ParseInt32(env, argv[0], type)) {
1560         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR, ParamCheckErrorMsgTemplate::TYPE_ALL_INT);
1561         return result;
1562     }
1563     if (type <= static_cast<int>(WebMessageType::NOTSUPPORT) || type > static_cast<int>(WebMessageType::ERROR)) {
1564         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1565         return result;
1566     }
1567     WebMessageExt *webMessageExt = nullptr;
1568     status = napi_unwrap(env, thisVar, (void **)&webMessageExt);
1569     if (status != napi_ok) {
1570         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1571             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "type"));
1572         WVLOG_E("NapiWebMessageExt::SetType napi_unwrap failed");
1573         return result;
1574     }
1575     if (!webMessageExt) {
1576         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1577             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NOT_NULL, "type"));
1578         WVLOG_E("NapiWebMessageExt::SetType webMessageExt is null");
1579         return result;
1580     }
1581     webMessageExt->SetType(type);
1582     return result;
1583 }
1584 
SetString(napi_env env, napi_callback_info info)1585 napi_value NapiWebMessageExt::SetString(napi_env env, napi_callback_info info)
1586 {
1587     WVLOG_D("NapiWebMessageExt::SetString start");
1588     napi_value thisVar = nullptr;
1589     napi_value result = nullptr;
1590     size_t argc = INTEGER_ONE;
1591     napi_value argv[INTEGER_ONE] = { 0 };
1592     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
1593     if (argc != INTEGER_ONE) {
1594         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1595             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
1596         return result;
1597     }
1598 
1599     std::string value;
1600     if (!NapiParseUtils::ParseString(env, argv[0], value)) {
1601         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1602             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "message", "string"));
1603         return result;
1604     }
1605     WebMessageExt *webMessageExt = nullptr;
1606     napi_status status = napi_unwrap(env, thisVar, (void **)&webMessageExt);
1607     if ((!webMessageExt) || (status != napi_ok)) {
1608         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1609             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "message"));
1610         return result;
1611     }
1612 
1613     int32_t type = webMessageExt->GetType();
1614     if (type != static_cast<int32_t>(WebMessageType::STRING)) {
1615         WVLOG_E("web message SetString error type:%{public}d", type);
1616         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1617         return result;
1618     }
1619     webMessageExt->SetString(value);
1620     return result;
1621 }
1622 
SetNumber(napi_env env, napi_callback_info info)1623 napi_value NapiWebMessageExt::SetNumber(napi_env env, napi_callback_info info)
1624 {
1625     WVLOG_D("NapiWebMessageExt::SetNumber start");
1626     napi_value thisVar = nullptr;
1627     napi_value result = nullptr;
1628     size_t argc = INTEGER_ONE;
1629     napi_value argv[INTEGER_ONE] = { 0 };
1630     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
1631     if (argc != INTEGER_ONE) {
1632         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1633             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
1634         return result;
1635     }
1636 
1637     double value = 0;
1638     if (!NapiParseUtils::ParseDouble(env, argv[0], value)) {
1639         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1640             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "message", "number"));
1641         return result;
1642     }
1643 
1644     WebMessageExt *webMessageExt = nullptr;
1645     napi_status status = napi_unwrap(env, thisVar, (void **)&webMessageExt);
1646     if ((!webMessageExt) || (status != napi_ok)) {
1647         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1648             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "message"));
1649         return result;
1650     }
1651 
1652     int32_t type = webMessageExt->GetType();
1653     if (type != static_cast<int32_t>(WebMessageType::NUMBER)) {
1654         WVLOG_E("web message SetNumber error type:%{public}d", type);
1655         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1656         return result;
1657     }
1658     webMessageExt->SetNumber(value);
1659     return result;
1660 }
1661 
SetBoolean(napi_env env, napi_callback_info info)1662 napi_value NapiWebMessageExt::SetBoolean(napi_env env, napi_callback_info info)
1663 {
1664     WVLOG_D("NapiWebMessageExt::SetBoolean start");
1665     napi_value thisVar = nullptr;
1666     napi_value result = nullptr;
1667     size_t argc = INTEGER_ONE;
1668     napi_value argv[INTEGER_ONE] = { 0 };
1669     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
1670     if (argc != INTEGER_ONE) {
1671         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1672             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
1673         return result;
1674     }
1675 
1676     bool value = 0;
1677     if (!NapiParseUtils::ParseBoolean(env, argv[0], value)) {
1678         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1679             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "message", "boolean"));
1680         return result;
1681     }
1682 
1683     WebMessageExt *webMessageExt = nullptr;
1684     napi_status status = napi_unwrap(env, thisVar, (void **)&webMessageExt);
1685     if ((!webMessageExt) || (status != napi_ok)) {
1686         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1687             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "message"));
1688         return result;
1689     }
1690 
1691     int32_t type = webMessageExt->GetType();
1692     if (type != static_cast<int32_t>(WebMessageType::BOOLEAN)) {
1693         WVLOG_E("web message SetBoolean error type:%{public}d", type);
1694         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1695         return result;
1696     }
1697     webMessageExt->SetBoolean(value);
1698     return result;
1699 }
1700 
SetArrayBuffer(napi_env env, napi_callback_info info)1701 napi_value NapiWebMessageExt::SetArrayBuffer(napi_env env, napi_callback_info info)
1702 {
1703     WVLOG_D("NapiWebMessageExt::SetArrayBuffer start");
1704     napi_value thisVar = nullptr;
1705     napi_value result = nullptr;
1706     size_t argc = INTEGER_ONE;
1707     napi_value argv[INTEGER_ONE] = { 0 };
1708     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
1709     if (argc != INTEGER_ONE) {
1710         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1711             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
1712         return result;
1713     }
1714 
1715     bool isArrayBuffer = false;
1716     NAPI_CALL(env, napi_is_arraybuffer(env, argv[INTEGER_ZERO], &isArrayBuffer));
1717     if (!isArrayBuffer) {
1718         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1719             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "message", "arrayBuffer"));
1720         return result;
1721     }
1722 
1723     uint8_t *arrBuf = nullptr;
1724     size_t byteLength = 0;
1725     napi_get_arraybuffer_info(env, argv[INTEGER_ZERO], (void**)&arrBuf, &byteLength);
1726     std::vector<uint8_t> vecData(arrBuf, arrBuf + byteLength);
1727     WebMessageExt *webMessageExt = nullptr;
1728     napi_status status = napi_unwrap(env, thisVar, (void **)&webMessageExt);
1729     if ((!webMessageExt) || (status != napi_ok)) {
1730         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1731             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "message"));
1732         return result;
1733     }
1734 
1735     int32_t type = webMessageExt->GetType();
1736     if (type != static_cast<int32_t>(WebMessageType::ARRAYBUFFER)) {
1737         WVLOG_E("web message SetArrayBuffer error type:%{public}d", type);
1738         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1739         return result;
1740     }
1741     webMessageExt->SetArrayBuffer(vecData);
1742     return result;
1743 }
1744 
SetArray(napi_env env, napi_callback_info info)1745 napi_value NapiWebMessageExt::SetArray(napi_env env, napi_callback_info info)
1746 {
1747     WVLOG_D("NapiWebMessageExt::SetArray start");
1748     napi_value thisVar = nullptr;
1749     napi_value result = nullptr;
1750     size_t argc = INTEGER_ONE;
1751     napi_value argv[INTEGER_ONE] = { 0 };
1752     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
1753     if (argc != INTEGER_ONE) {
1754         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1755             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
1756         return result;
1757     }
1758     bool isArray = false;
1759     NAPI_CALL(env, napi_is_array(env, argv[INTEGER_ZERO], &isArray));
1760     if (!isArray) {
1761         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1762             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "message", "array"));
1763         return result;
1764     }
1765     WebMessageExt *webMessageExt = nullptr;
1766     napi_status status = napi_unwrap(env, thisVar, (void **)&webMessageExt);
1767     if ((!webMessageExt) || (status != napi_ok)) {
1768         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1769             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "message"));
1770         return result;
1771     }
1772     int32_t type = webMessageExt->GetType();
1773     if (type != static_cast<int32_t>(WebMessageType::ARRAY)) {
1774         WVLOG_E("web message SetArray error type:%{public}d", type);
1775         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1776         return result;
1777     }
1778     bool isDouble = false;
1779     napi_valuetype valueType = GetArrayValueType(env, argv[INTEGER_ZERO], isDouble);
1780     if (valueType == napi_undefined) {
1781         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1782             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "message", "number"));
1783         return result;
1784     }
1785     using SetArrayHandler = std::function<void(napi_env, napi_value, WebMessageExt*)>;
1786     const std::unordered_map<napi_valuetype, SetArrayHandler> functionMap = {
1787         { napi_boolean, SetArrayHandlerBoolean },
1788         { napi_string, SetArrayHandlerString },
1789         { napi_number, [isDouble](napi_env env, napi_value array, WebMessageExt* msgExt) {
1790             isDouble ? SetArrayHandlerDouble(env, array, msgExt)
1791                      : SetArrayHandlerInteger(env, array, msgExt);
1792         } }
1793     };
1794     auto it = functionMap.find(valueType);
1795     if (it != functionMap.end()) {
1796         it->second(env, argv[INTEGER_ZERO], webMessageExt);
1797     }
1798     return result;
1799 }
1800 
SetError(napi_env env, napi_callback_info info)1801 napi_value NapiWebMessageExt::SetError(napi_env env, napi_callback_info info)
1802 {
1803     WVLOG_D("NapiWebMessageExt::SetError start");
1804     napi_value thisVar = nullptr;
1805     napi_value result = nullptr;
1806     size_t argc = INTEGER_ONE;
1807     napi_value argv[INTEGER_ONE] = { 0 };
1808     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
1809     if (argc != INTEGER_ONE) {
1810         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1811             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
1812         return result;
1813     }
1814 
1815     bool isError = false;
1816     NAPI_CALL(env, napi_is_error(env, argv[INTEGER_ZERO], &isError));
1817     if (!isError) {
1818         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1819             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "message", "error"));
1820         return result;
1821     }
1822 
1823     napi_value nameObj = 0;
1824     napi_get_named_property(env, argv[INTEGER_ZERO], "name", &nameObj);
1825     std::string nameVal;
1826     if (!NapiParseUtils::ParseString(env, nameObj, nameVal)) {
1827         return result;
1828     }
1829 
1830     napi_value msgObj = 0;
1831     napi_get_named_property(env, argv[INTEGER_ZERO], "message", &msgObj);
1832     std::string msgVal;
1833     if (!NapiParseUtils::ParseString(env, msgObj, msgVal)) {
1834         return result;
1835     }
1836 
1837     WebMessageExt *webMessageExt = nullptr;
1838     napi_status status = napi_unwrap(env, thisVar, (void **)&webMessageExt);
1839     if ((!webMessageExt) || (status != napi_ok)) {
1840         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1841             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "message"));
1842         return result;
1843     }
1844 
1845     int32_t type = webMessageExt->GetType();
1846     if (type != static_cast<int32_t>(WebMessageType::ERROR)) {
1847         WVLOG_E("web message SetError error type:%{public}d", type);
1848         BusinessError::ThrowErrorByErrcode(env, TYPE_NOT_MATCH_WITCH_VALUE);
1849         return result;
1850     }
1851     webMessageExt->SetError(nameVal, msgVal);
1852     return result;
1853 }
1854 
CreateWebMessagePorts(napi_env env, napi_callback_info info)1855 napi_value NapiWebviewController::CreateWebMessagePorts(napi_env env, napi_callback_info info)
1856 {
1857     WVLOG_D("create web message port");
1858     napi_value thisVar = nullptr;
1859     napi_value result = nullptr;
1860     size_t argc = INTEGER_ONE;
1861     napi_value argv[INTEGER_ONE] = { 0 };
1862     bool isExtentionType = false;
1863     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
1864     if (argc != INTEGER_ZERO && argc != INTEGER_ONE) {
1865         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1866             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_TWO, "zero", "one"));
1867         return result;
1868     }
1869 
1870     if (argc == INTEGER_ONE) {
1871         if (!NapiParseUtils::ParseBoolean(env, argv[0], isExtentionType)) {
1872             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1873                 NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "isExtentionType", "boolean"));
1874             return result;
1875         }
1876     }
1877 
1878     WebviewController *webviewController = nullptr;
1879     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webviewController));
1880     if (webviewController == nullptr || !webviewController->IsInit()) {
1881         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
1882         WVLOG_E("create message port failed, napi unwrap webviewController failed");
1883         return nullptr;
1884     }
1885     int32_t nwebId = webviewController->GetWebId();
1886     std::vector<std::string> ports = webviewController->CreateWebMessagePorts();
1887     if (ports.size() != INTEGER_TWO) {
1888         WVLOG_E("create web message port failed");
1889         return result;
1890     }
1891     napi_value msgPortcons = nullptr;
1892     NAPI_CALL(env, napi_get_reference_value(env, g_classWebMsgPort, &msgPortcons));
1893     napi_create_array(env, &result);
1894     napi_value consParam[INTEGER_TWO][INTEGER_THREE] = {{0}};
1895     for (uint32_t i = 0; i < INTEGER_TWO; i++) {
1896         napi_value msgPortObj = nullptr;
1897         NAPI_CALL(env, napi_create_int32(env, nwebId, &consParam[i][INTEGER_ZERO]));
1898         NAPI_CALL(env, napi_create_string_utf8(env, ports[i].c_str(), ports[i].length(), &consParam[i][INTEGER_ONE]));
1899         NAPI_CALL(env, napi_get_boolean(env, isExtentionType, &consParam[i][INTEGER_TWO]));
1900         NAPI_CALL(env, napi_new_instance(env, msgPortcons, INTEGER_THREE, consParam[i], &msgPortObj));
1901         napi_value jsExtention;
1902         napi_get_boolean(env, isExtentionType, &jsExtention);
1903         napi_set_named_property(env, msgPortObj, "isExtentionType", jsExtention);
1904 
1905         napi_set_element(env, result, i, msgPortObj);
1906     }
1907 
1908     return result;
1909 }
1910 
GetSendPorts(napi_env env, napi_value argv, std::vector<std::string>& sendPorts)1911 bool GetSendPorts(napi_env env, napi_value argv, std::vector<std::string>& sendPorts)
1912 {
1913     uint32_t arrayLen = 0;
1914     napi_get_array_length(env, argv, &arrayLen);
1915     if (arrayLen == 0) {
1916         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
1917         return false;
1918     }
1919 
1920     napi_valuetype valueType = napi_undefined;
1921     for (uint32_t i = 0; i < arrayLen; i++) {
1922         napi_value portItem = nullptr;
1923         napi_get_element(env, argv, i, &portItem);
1924         napi_typeof(env, portItem, &valueType);
1925         if (valueType != napi_object) {
1926             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
1927             return false;
1928         }
1929         WebMessagePort *msgPort = nullptr;
1930         napi_status status = napi_unwrap(env, portItem, (void **)&msgPort);
1931         if ((!msgPort) || (status != napi_ok)) {
1932             WVLOG_E("post port to html failed, napi unwrap msg port fail");
1933             return false;
1934         }
1935         std::string portHandle = msgPort->GetPortHandle();
1936         sendPorts.emplace_back(portHandle);
1937     }
1938     return true;
1939 }
1940 
PostMessage(napi_env env, napi_callback_info info)1941 napi_value NapiWebviewController::PostMessage(napi_env env, napi_callback_info info)
1942 {
1943     WVLOG_D("post message port");
1944     napi_value thisVar = nullptr;
1945     napi_value result = nullptr;
1946     size_t argc = INTEGER_THREE;
1947     napi_value argv[INTEGER_THREE];
1948     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
1949     if (argc != INTEGER_THREE) {
1950         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1951             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "three"));
1952         return result;
1953     }
1954 
1955     std::string portName;
1956     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], portName)) {
1957         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1958             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "name", "string"));
1959         return result;
1960     }
1961 
1962     bool isArray = false;
1963     NAPI_CALL(env, napi_is_array(env, argv[INTEGER_ONE], &isArray));
1964     if (!isArray) {
1965         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1966             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "ports", "array"));
1967         return result;
1968     }
1969     std::vector<std::string> sendPorts;
1970     if (!GetSendPorts(env, argv[INTEGER_ONE], sendPorts)) {
1971         WVLOG_E("post port to html failed, getSendPorts fail");
1972         return result;
1973     }
1974 
1975     std::string urlStr;
1976     if (!NapiParseUtils::ParseString(env, argv[INTEGER_TWO], urlStr)) {
1977         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
1978             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "uri", "string"));
1979         return result;
1980     }
1981 
1982     WebviewController *webviewController = nullptr;
1983     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webviewController));
1984     if (webviewController == nullptr || !webviewController->IsInit()) {
1985         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
1986         WVLOG_E("post port to html failed, napi unwrap webviewController failed");
1987         return nullptr;
1988     }
1989 
1990     webviewController->PostWebMessage(portName, sendPorts, urlStr);
1991     NAPI_CALL(env, napi_get_undefined(env, &result));
1992 
1993     return result;
1994 }
1995 
JsConstructor(napi_env env, napi_callback_info info)1996 napi_value NapiWebMessagePort::JsConstructor(napi_env env, napi_callback_info info)
1997 {
1998     WVLOG_D("web message port construct");
1999     napi_value thisVar = nullptr;
2000     size_t argc = INTEGER_THREE;
2001     napi_value argv[INTEGER_THREE] = {0};
2002     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
2003 
2004     int32_t webId = -1;
2005     if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_ZERO], webId)) {
2006         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
2007         return nullptr;
2008     }
2009 
2010     std::string portHandle;
2011     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ONE], portHandle)) {
2012         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
2013         return nullptr;
2014     }
2015 
2016     bool isExtentionType = false;
2017     if (!NapiParseUtils::ParseBoolean(env, argv[INTEGER_TWO], isExtentionType)) {
2018         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
2019         return nullptr;
2020     }
2021 
2022     WebMessagePort *msgPort = new (std::nothrow) WebMessagePort(webId, portHandle, isExtentionType);
2023     if (msgPort == nullptr) {
2024         WVLOG_E("new msg port failed");
2025         return nullptr;
2026     }
2027     NAPI_CALL(env, napi_wrap(env, thisVar, msgPort,
2028         [](napi_env env, void *data, void *hint) {
2029             WebMessagePort *msgPort = static_cast<WebMessagePort *>(data);
2030             delete msgPort;
2031         },
2032         nullptr, nullptr));
2033     return thisVar;
2034 }
2035 
Close(napi_env env, napi_callback_info info)2036 napi_value NapiWebMessagePort::Close(napi_env env, napi_callback_info info)
2037 {
2038     WVLOG_D("close message port");
2039     napi_value thisVar = nullptr;
2040     napi_value result = nullptr;
2041     NAPI_CALL(env, napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr));
2042 
2043     WebMessagePort *msgPort = nullptr;
2044     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&msgPort));
2045     if (msgPort == nullptr) {
2046         WVLOG_E("close message port failed, napi unwrap msg port failed");
2047         return nullptr;
2048     }
2049     ErrCode ret = msgPort->ClosePort();
2050     if (ret != NO_ERROR) {
2051         BusinessError::ThrowErrorByErrcode(env, ret);
2052         return result;
2053     }
2054     NAPI_CALL(env, napi_get_undefined(env, &result));
2055 
2056     return result;
2057 }
2058 
PostMessageEventMsgHandler(napi_env env, napi_value argv, napi_valuetype valueType, bool isArrayBuffer, std::shared_ptr<NWebMessage> webMsg)2059 bool PostMessageEventMsgHandler(napi_env env, napi_value argv, napi_valuetype valueType, bool isArrayBuffer,
2060     std::shared_ptr<NWebMessage> webMsg)
2061 {
2062     if (valueType == napi_string) {
2063         size_t bufferSize = 0;
2064         napi_get_value_string_utf8(env, argv, nullptr, 0, &bufferSize);
2065         if (bufferSize > UINT_MAX) {
2066             WVLOG_E("String length is too long");
2067             return false;
2068         }
2069         char* stringValue = new (std::nothrow) char[bufferSize + 1];
2070         if (stringValue == nullptr) {
2071             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
2072             return false;
2073         }
2074         size_t jsStringLength = 0;
2075         napi_get_value_string_utf8(env, argv, stringValue, bufferSize + 1, &jsStringLength);
2076         std::string message(stringValue);
2077         delete [] stringValue;
2078         stringValue = nullptr;
2079 
2080         webMsg->SetType(NWebValue::Type::STRING);
2081         webMsg->SetString(message);
2082     } else if (isArrayBuffer) {
2083         uint8_t *arrBuf = nullptr;
2084         size_t byteLength = 0;
2085         napi_get_arraybuffer_info(env, argv, (void**)&arrBuf, &byteLength);
2086         std::vector<uint8_t> vecData(arrBuf, arrBuf + byteLength);
2087         webMsg->SetType(NWebValue::Type::BINARY);
2088         webMsg->SetBinary(vecData);
2089     }
2090     return true;
2091 }
2092 
PostMessageEvent(napi_env env, napi_callback_info info)2093 napi_value NapiWebMessagePort::PostMessageEvent(napi_env env, napi_callback_info info)
2094 {
2095     WVLOG_D("message port post message");
2096     napi_value thisVar = nullptr;
2097     napi_value result = nullptr;
2098     size_t argc = INTEGER_ONE;
2099     napi_value argv[INTEGER_ONE];
2100     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
2101     if (argc != INTEGER_ONE) {
2102         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2103             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
2104         return result;
2105     }
2106     napi_valuetype valueType = napi_undefined;
2107     napi_typeof(env, argv[INTEGER_ZERO], &valueType);
2108 
2109     bool isArrayBuffer = false;
2110     NAPI_CALL(env, napi_is_arraybuffer(env, argv[INTEGER_ZERO], &isArrayBuffer));
2111     if (valueType != napi_string && !isArrayBuffer) {
2112         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2113             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "message"));
2114         return result;
2115     }
2116 
2117     auto webMsg = std::make_shared<OHOS::NWeb::NWebMessage>(NWebValue::Type::NONE);
2118     if (!PostMessageEventMsgHandler(env, argv[INTEGER_ZERO], valueType, isArrayBuffer, webMsg)) {
2119         WVLOG_E("post message failed, PostMessageEventMsgHandler failed");
2120         return result;
2121     }
2122 
2123     WebMessagePort *msgPort = nullptr;
2124     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&msgPort));
2125     if (msgPort == nullptr) {
2126         WVLOG_E("post message failed, napi unwrap msg port failed");
2127         return nullptr;
2128     }
2129     ErrCode ret = msgPort->PostPortMessage(webMsg);
2130     if (ret != NO_ERROR) {
2131         BusinessError::ThrowErrorByErrcode(env, ret);
2132         return result;
2133     }
2134     NAPI_CALL(env, napi_get_undefined(env, &result));
2135 
2136     return result;
2137 }
2138 
PostMessageEventExt(napi_env env, napi_callback_info info)2139 napi_value NapiWebMessagePort::PostMessageEventExt(napi_env env, napi_callback_info info)
2140 {
2141     WVLOG_D("message PostMessageEventExt start");
2142     napi_value thisVar = nullptr;
2143     napi_value result = nullptr;
2144     size_t argc = INTEGER_ONE;
2145     napi_value argv[INTEGER_ONE];
2146     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
2147     if (argc != INTEGER_ONE) {
2148         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2149             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
2150         return result;
2151     }
2152     napi_valuetype valueType = napi_undefined;
2153     napi_typeof(env, argv[INTEGER_ZERO], &valueType);
2154     if (valueType != napi_object) {
2155         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2156             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "message"));
2157         return result;
2158     }
2159 
2160     WebMessageExt *webMessageExt = nullptr;
2161     NAPI_CALL(env, napi_unwrap(env, argv[INTEGER_ZERO], (void **)&webMessageExt));
2162     if (webMessageExt == nullptr) {
2163         WVLOG_E("post message failed, napi unwrap msg port failed");
2164         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2165             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NOT_NULL, "message"));
2166         return nullptr;
2167     }
2168 
2169     WebMessagePort *msgPort = nullptr;
2170     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&msgPort));
2171     if (msgPort == nullptr) {
2172         WVLOG_E("post message failed, napi unwrap msg port failed");
2173         return nullptr;
2174     }
2175 
2176     if (!msgPort->IsExtentionType()) {
2177         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2178             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "message"));
2179         return result;
2180     }
2181 
2182     ErrCode ret = msgPort->PostPortMessage(webMessageExt->GetData());
2183     if (ret != NO_ERROR) {
2184         BusinessError::ThrowErrorByErrcode(env, ret);
2185         return result;
2186     }
2187     NAPI_CALL(env, napi_get_undefined(env, &result));
2188 
2189     return result;
2190 }
2191 
2192 
OnMessageEventExt(napi_env env, napi_callback_info info)2193 napi_value NapiWebMessagePort::OnMessageEventExt(napi_env env, napi_callback_info info)
2194 {
2195     WVLOG_D("message port set OnMessageEventExt callback");
2196     napi_value thisVar = nullptr;
2197     napi_value result = nullptr;
2198     size_t argc = INTEGER_ONE;
2199     napi_value argv[INTEGER_ONE];
2200     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
2201     if (argc != INTEGER_ONE) {
2202         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2203             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
2204         return result;
2205     }
2206     napi_valuetype valueType = napi_undefined;
2207     napi_typeof(env, argv[INTEGER_ZERO], &valueType);
2208     if (valueType != napi_function) {
2209         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2210             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "callback", "function"));
2211         return result;
2212     }
2213 
2214     napi_ref onMsgEventFunc = nullptr;
2215     NAPI_CALL(env, napi_create_reference(env, argv[INTEGER_ZERO], INTEGER_ONE, &onMsgEventFunc));
2216 
2217     auto callbackImpl = std::make_shared<NWebValueCallbackImpl>(env, onMsgEventFunc, true);
2218 
2219     WebMessagePort *msgPort = nullptr;
2220     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&msgPort));
2221     if (msgPort == nullptr) {
2222         WVLOG_E("set message event callback failed, napi unwrap msg port failed");
2223         napi_delete_reference(env, onMsgEventFunc);
2224         return nullptr;
2225     }
2226     ErrCode ret = msgPort->SetPortMessageCallback(callbackImpl);
2227     if (ret != NO_ERROR) {
2228         BusinessError::ThrowErrorByErrcode(env, ret);
2229     }
2230     NAPI_CALL(env, napi_get_undefined(env, &result));
2231     return result;
2232 }
2233 
UvWebMsgOnReceiveCbDataHandler(NapiWebMessagePort::WebMsgPortParam *data, napi_value& result)2234 bool UvWebMsgOnReceiveCbDataHandler(NapiWebMessagePort::WebMsgPortParam *data, napi_value& result)
2235 {
2236     if (data->extention_) {
2237         napi_value webMsgExt = nullptr;
2238         napi_status status = napi_get_reference_value(data->env_, g_webMsgExtClassRef, &webMsgExt);
2239         if (status != napi_status::napi_ok) {
2240             WVLOG_E("napi_get_reference_value failed.");
2241             return false;
2242         }
2243         status = napi_new_instance(data->env_, webMsgExt, 0, NULL, &result);
2244         if (status != napi_status::napi_ok) {
2245             WVLOG_E("napi_new_instance failed.");
2246             return false;
2247         }
2248 
2249         WebMessageExt *webMessageExt = new (std::nothrow) WebMessageExt(data->msg_);
2250         if (webMessageExt == nullptr) {
2251             WVLOG_E("new WebMessageExt failed.");
2252             return false;
2253         }
2254 
2255         status = napi_wrap(data->env_, result, webMessageExt,
2256             [](napi_env env, void *data, void *hint) {
2257                 WebMessageExt *webMessageExt = static_cast<WebMessageExt *>(data);
2258                 delete webMessageExt;
2259             },
2260             nullptr, nullptr);
2261         if (status != napi_status::napi_ok) {
2262             WVLOG_E("napi_wrap failed.");
2263             return false;
2264         }
2265     } else {
2266         NapiParseUtils::ConvertNWebToNapiValue(data->env_, data->msg_, result);
2267     }
2268     return true;
2269 }
2270 
UvWebMessageOnReceiveValueCallback(uv_work_t *work, int status)2271 void NWebValueCallbackImpl::UvWebMessageOnReceiveValueCallback(uv_work_t *work, int status)
2272 {
2273     if (work == nullptr) {
2274         WVLOG_E("uv work is null");
2275         return;
2276     }
2277     NapiWebMessagePort::WebMsgPortParam *data = reinterpret_cast<NapiWebMessagePort::WebMsgPortParam*>(work->data);
2278     if (data == nullptr) {
2279         WVLOG_E("WebMsgPortParam is null");
2280         delete work;
2281         work = nullptr;
2282         return;
2283     }
2284     napi_handle_scope scope = nullptr;
2285     napi_open_handle_scope(data->env_, &scope);
2286     if (scope == nullptr) {
2287         delete work;
2288         work = nullptr;
2289         return;
2290     }
2291     napi_value result[INTEGER_ONE] = {0};
2292     if (!UvWebMsgOnReceiveCbDataHandler(data, result[INTEGER_ZERO])) {
2293         delete work;
2294         work = nullptr;
2295         napi_close_handle_scope(data->env_, scope);
2296         return;
2297     }
2298 
2299     napi_value onMsgEventFunc = nullptr;
2300     napi_get_reference_value(data->env_, data->callback_, &onMsgEventFunc);
2301     napi_value placeHodler = nullptr;
2302     napi_call_function(data->env_, nullptr, onMsgEventFunc, INTEGER_ONE, &result[INTEGER_ZERO], &placeHodler);
2303 
2304     std::unique_lock<std::mutex> lock(data->mutex_);
2305     data->ready_ = true;
2306     data->condition_.notify_all();
2307     napi_close_handle_scope(data->env_, scope);
2308 }
2309 
InvokeWebMessageCallback(NapiWebMessagePort::WebMsgPortParam *data)2310 static void InvokeWebMessageCallback(NapiWebMessagePort::WebMsgPortParam *data)
2311 {
2312     napi_handle_scope scope = nullptr;
2313     napi_open_handle_scope(data->env_, &scope);
2314     if (scope == nullptr) {
2315         WVLOG_E("scope is null");
2316         return;
2317     }
2318     napi_value result[INTEGER_ONE] = {0};
2319     if (!UvWebMsgOnReceiveCbDataHandler(data, result[INTEGER_ZERO])) {
2320         WVLOG_E("get result failed");
2321         napi_close_handle_scope(data->env_, scope);
2322         return;
2323     }
2324 
2325     napi_value onMsgEventFunc = nullptr;
2326     napi_get_reference_value(data->env_, data->callback_, &onMsgEventFunc);
2327     napi_value placeHodler = nullptr;
2328     napi_call_function(data->env_, nullptr, onMsgEventFunc, INTEGER_ONE, &result[INTEGER_ZERO], &placeHodler);
2329 
2330     napi_close_handle_scope(data->env_, scope);
2331 }
2332 
OnReceiveValue(std::shared_ptr<NWebMessage> result)2333 void NWebValueCallbackImpl::OnReceiveValue(std::shared_ptr<NWebMessage> result)
2334 {
2335     WVLOG_D("message port received msg");
2336     uv_loop_s *loop = nullptr;
2337     uv_work_t *work = nullptr;
2338     napi_get_uv_event_loop(env_, &loop);
2339     auto engine = reinterpret_cast<NativeEngine*>(env_);
2340     if (loop == nullptr) {
2341         WVLOG_E("get uv event loop failed");
2342         return;
2343     }
2344     work = new (std::nothrow) uv_work_t;
2345     if (work == nullptr) {
2346         WVLOG_E("new uv work failed");
2347         return;
2348     }
2349     NapiWebMessagePort::WebMsgPortParam *param = new (std::nothrow) NapiWebMessagePort::WebMsgPortParam();
2350     if (param == nullptr) {
2351         WVLOG_E("new WebMsgPortParam failed");
2352         delete work;
2353         return;
2354     }
2355     param->env_ = env_;
2356     param->callback_ = callback_;
2357     param->msg_ = result;
2358     param->extention_ = extention_;
2359     if (pthread_self() == engine->GetTid()) {
2360         InvokeWebMessageCallback(param);
2361     } else {
2362         work->data = reinterpret_cast<void*>(param);
2363         uv_queue_work_with_qos(
2364             loop, work, [](uv_work_t* work) {}, UvWebMessageOnReceiveValueCallback, uv_qos_user_initiated);
2365 
2366         {
2367             std::unique_lock<std::mutex> lock(param->mutex_);
2368             param->condition_.wait(lock, [&param] { return param->ready_; });
2369         }
2370     }
2371 
2372     if (param != nullptr) {
2373         delete param;
2374         param = nullptr;
2375     }
2376     if (work != nullptr) {
2377         delete work;
2378         work = nullptr;
2379     }
2380 }
2381 
UvNWebValueCallbackImplThreadWoker(uv_work_t *work, int status)2382 void UvNWebValueCallbackImplThreadWoker(uv_work_t *work, int status)
2383 {
2384     if (work == nullptr) {
2385         WVLOG_E("uv work is null");
2386         return;
2387     }
2388     NapiWebMessagePort::WebMsgPortParam *data = reinterpret_cast<NapiWebMessagePort::WebMsgPortParam*>(work->data);
2389     if (data == nullptr) {
2390         WVLOG_E("WebMsgPortParam is null");
2391         delete work;
2392         return;
2393     }
2394 
2395     napi_delete_reference(data->env_, data->callback_);
2396     delete data;
2397     data = nullptr;
2398     delete work;
2399     work = nullptr;
2400 }
2401 
~NWebValueCallbackImpl()2402 NWebValueCallbackImpl::~NWebValueCallbackImpl()
2403 {
2404     WVLOG_D("~NWebValueCallbackImpl");
2405     uv_loop_s *loop = nullptr;
2406     uv_work_t *work = nullptr;
2407     napi_get_uv_event_loop(env_, &loop);
2408     if (loop == nullptr) {
2409         WVLOG_E("get uv event loop failed");
2410         return;
2411     }
2412     work = new (std::nothrow) uv_work_t;
2413     if (work == nullptr) {
2414         WVLOG_E("new uv work failed");
2415         return;
2416     }
2417     NapiWebMessagePort::WebMsgPortParam *param = new (std::nothrow) NapiWebMessagePort::WebMsgPortParam();
2418     if (param == nullptr) {
2419         WVLOG_E("new WebMsgPortParam failed");
2420         delete work;
2421         return;
2422     }
2423     param->env_ = env_;
2424     param->callback_ = callback_;
2425     work->data = reinterpret_cast<void*>(param);
2426     int ret = uv_queue_work_with_qos(
2427         loop, work, [](uv_work_t *work) {}, UvNWebValueCallbackImplThreadWoker, uv_qos_user_initiated);
2428     if (ret != 0) {
2429         if (param != nullptr) {
2430             delete param;
2431             param = nullptr;
2432         }
2433         if (work != nullptr) {
2434             delete work;
2435             work = nullptr;
2436         }
2437     }
2438 }
2439 
OnMessageEvent(napi_env env, napi_callback_info info)2440 napi_value NapiWebMessagePort::OnMessageEvent(napi_env env, napi_callback_info info)
2441 {
2442     WVLOG_D("message port set OnMessageEvent callback");
2443     napi_value thisVar = nullptr;
2444     napi_value result = nullptr;
2445     size_t argc = INTEGER_ONE;
2446     napi_value argv[INTEGER_ONE];
2447     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
2448     if (argc != INTEGER_ONE) {
2449         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2450             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
2451         return result;
2452     }
2453     napi_valuetype valueType = napi_undefined;
2454     napi_typeof(env, argv[INTEGER_ZERO], &valueType);
2455     if (valueType != napi_function) {
2456         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2457             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "callback", "function"));
2458         return result;
2459     }
2460 
2461     napi_ref onMsgEventFunc = nullptr;
2462     NAPI_CALL(env, napi_create_reference(env, argv[INTEGER_ZERO], INTEGER_ONE, &onMsgEventFunc));
2463 
2464     auto callbackImpl = std::make_shared<NWebValueCallbackImpl>(env, onMsgEventFunc, false);
2465 
2466     WebMessagePort *msgPort = nullptr;
2467     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&msgPort));
2468     if (msgPort == nullptr) {
2469         WVLOG_E("set message event callback failed, napi unwrap msg port failed");
2470         return nullptr;
2471     }
2472     ErrCode ret = msgPort->SetPortMessageCallback(callbackImpl);
2473     if (ret != NO_ERROR) {
2474         BusinessError::ThrowErrorByErrcode(env, ret);
2475     }
2476     NAPI_CALL(env, napi_get_undefined(env, &result));
2477     return result;
2478 }
2479 
ZoomIn(napi_env env, napi_callback_info info)2480 napi_value NapiWebviewController::ZoomIn(napi_env env, napi_callback_info info)
2481 {
2482     napi_value result = nullptr;
2483     WebviewController *webviewController = GetWebviewController(env, info);
2484     if (!webviewController) {
2485         return nullptr;
2486     }
2487 
2488     ErrCode ret = webviewController->ZoomIn();
2489     if (ret != NO_ERROR) {
2490         if (ret == NWEB_ERROR) {
2491             WVLOG_E("ZoomIn failed.");
2492             return nullptr;
2493         }
2494         BusinessError::ThrowErrorByErrcode(env, ret);
2495     }
2496 
2497     NAPI_CALL(env, napi_get_undefined(env, &result));
2498     return result;
2499 }
2500 
ZoomOut(napi_env env, napi_callback_info info)2501 napi_value NapiWebviewController::ZoomOut(napi_env env, napi_callback_info info)
2502 {
2503     napi_value result = nullptr;
2504     WebviewController *webviewController = GetWebviewController(env, info);
2505     if (!webviewController) {
2506         return nullptr;
2507     }
2508 
2509     ErrCode ret = webviewController->ZoomOut();
2510     if (ret != NO_ERROR) {
2511         if (ret == NWEB_ERROR) {
2512             WVLOG_E("ZoomOut failed.");
2513             return nullptr;
2514         }
2515         BusinessError::ThrowErrorByErrcode(env, ret);
2516     }
2517 
2518     NAPI_CALL(env, napi_get_undefined(env, &result));
2519     return result;
2520 }
2521 
GetWebId(napi_env env, napi_callback_info info)2522 napi_value NapiWebviewController::GetWebId(napi_env env, napi_callback_info info)
2523 {
2524     napi_value result = nullptr;
2525     WebviewController *webviewController = GetWebviewController(env, info);
2526     if (!webviewController) {
2527         return nullptr;
2528     }
2529 
2530     int32_t webId = webviewController->GetWebId();
2531     napi_create_int32(env, webId, &result);
2532 
2533     return result;
2534 }
2535 
GetUserAgent(napi_env env, napi_callback_info info)2536 napi_value NapiWebviewController::GetUserAgent(napi_env env, napi_callback_info info)
2537 {
2538     napi_value result = nullptr;
2539     WebviewController *webviewController = GetWebviewController(env, info);
2540     if (!webviewController) {
2541         return nullptr;
2542     }
2543 
2544     std::string userAgent = "";
2545     userAgent = webviewController->GetUserAgent();
2546     napi_create_string_utf8(env, userAgent.c_str(), userAgent.length(), &result);
2547 
2548     return result;
2549 }
2550 
GetCustomUserAgent(napi_env env, napi_callback_info info)2551 napi_value NapiWebviewController::GetCustomUserAgent(napi_env env, napi_callback_info info)
2552 {
2553     napi_value thisVar = nullptr;
2554     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
2555 
2556     WebviewController *webviewController = nullptr;
2557     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
2558     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
2559         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
2560         return nullptr;
2561     }
2562 
2563     napi_value result = nullptr;
2564     std::string userAgent = webviewController->GetCustomUserAgent();
2565     napi_create_string_utf8(env, userAgent.c_str(), userAgent.length(), &result);
2566     return result;
2567 }
2568 
SetCustomUserAgent(napi_env env, napi_callback_info info)2569 napi_value NapiWebviewController::SetCustomUserAgent(napi_env env, napi_callback_info info)
2570 {
2571     napi_value thisVar = nullptr;
2572     napi_value result = nullptr;
2573     size_t argc = INTEGER_ONE;
2574     napi_value argv[INTEGER_ONE];
2575     NAPI_CALL(env, napi_get_undefined(env, &result));
2576 
2577     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
2578     if (argc != INTEGER_ONE) {
2579         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2580             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
2581         return result;
2582     }
2583 
2584     std::string userAgent;
2585     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], userAgent)) {
2586         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2587             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "userAgent", "string"));
2588         return result;
2589     }
2590 
2591     WebviewController *webviewController = nullptr;
2592     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
2593     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
2594         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
2595         return result;
2596     }
2597     ErrCode ret = webviewController->SetCustomUserAgent(userAgent);
2598     if (ret != NO_ERROR) {
2599         BusinessError::ThrowErrorByErrcode(env, ret);
2600     }
2601     return result;
2602 }
2603 
GetTitle(napi_env env, napi_callback_info info)2604 napi_value NapiWebviewController::GetTitle(napi_env env, napi_callback_info info)
2605 {
2606     napi_value result = nullptr;
2607     WebviewController *webviewController = GetWebviewController(env, info);
2608     if (!webviewController) {
2609         return nullptr;
2610     }
2611 
2612     std::string title = "";
2613     title = webviewController->GetTitle();
2614     napi_create_string_utf8(env, title.c_str(), title.length(), &result);
2615 
2616     return result;
2617 }
2618 
GetPageHeight(napi_env env, napi_callback_info info)2619 napi_value NapiWebviewController::GetPageHeight(napi_env env, napi_callback_info info)
2620 {
2621     napi_value result = nullptr;
2622     WebviewController *webviewController = GetWebviewController(env, info);
2623     if (!webviewController) {
2624         return nullptr;
2625     }
2626 
2627     int32_t pageHeight = webviewController->GetPageHeight();
2628     napi_create_int32(env, pageHeight, &result);
2629 
2630     return result;
2631 }
2632 
BackOrForward(napi_env env, napi_callback_info info)2633 napi_value NapiWebviewController::BackOrForward(napi_env env, napi_callback_info info)
2634 {
2635     napi_value thisVar = nullptr;
2636     napi_value result = nullptr;
2637     size_t argc = INTEGER_ONE;
2638     napi_value argv[INTEGER_ONE] = {0};
2639     void* data = nullptr;
2640     napi_get_cb_info(env, info, &argc, argv, &thisVar, &data);
2641 
2642     if (argc != INTEGER_ONE) {
2643         WVLOG_E("Requires 1 parameters.");
2644         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2645             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
2646         return nullptr;
2647     }
2648 
2649     int32_t step = -1;
2650     if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_ZERO], step)) {
2651         WVLOG_E("Parameter is not integer number type.");
2652         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2653             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "step", "number"));
2654         return nullptr;
2655     }
2656 
2657     WebviewController *webviewController = nullptr;
2658     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
2659     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
2660         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
2661         return nullptr;
2662     }
2663 
2664     ErrCode ret = webviewController->BackOrForward(step);
2665     if (ret != NO_ERROR) {
2666         BusinessError::ThrowErrorByErrcode(env, ret);
2667     }
2668 
2669     NAPI_CALL(env, napi_get_undefined(env, &result));
2670     return result;
2671 }
2672 
StoreWebArchive(napi_env env, napi_callback_info info)2673 napi_value NapiWebviewController::StoreWebArchive(napi_env env, napi_callback_info info)
2674 {
2675     napi_value thisVar = nullptr;
2676     napi_value result = nullptr;
2677     size_t argc = INTEGER_ONE;
2678     size_t argcPromise = INTEGER_TWO;
2679     size_t argcCallback = INTEGER_THREE;
2680     napi_value argv[INTEGER_THREE] = { 0 };
2681 
2682     napi_get_undefined(env, &result);
2683     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
2684 
2685     if (argc != argcPromise && argc != argcCallback) {
2686         BusinessError::ThrowErrorByErrcode(env, NWebError::PARAM_CHECK_ERROR,
2687             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_TWO, "two", "three"));
2688         return result;
2689     }
2690     std::string baseName;
2691     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], baseName)) {
2692         BusinessError::ThrowErrorByErrcode(env, NWebError::PARAM_CHECK_ERROR,
2693             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "baseName", "string"));
2694         return result;
2695     }
2696 
2697     if (baseName.empty()) {
2698         BusinessError::ThrowErrorByErrcode(env, NWebError::PARAM_CHECK_ERROR,
2699             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NOT_NULL, "baseName"));
2700         return result;
2701     }
2702 
2703     bool autoName = false;
2704     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
2705     if (!NapiParseUtils::ParseBoolean(env, argv[INTEGER_ONE], autoName)) {
2706         BusinessError::ThrowErrorByErrcode(env, NWebError::PARAM_CHECK_ERROR,
2707             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "autoName", "boolean"));
2708         return result;
2709     }
2710 
2711     if (argc == argcCallback) {
2712         napi_valuetype valueType = napi_null;
2713         napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
2714         napi_typeof(env, argv[argcCallback - 1], &valueType);
2715         if (valueType != napi_function) {
2716             BusinessError::ThrowErrorByErrcode(env, NWebError::PARAM_CHECK_ERROR,
2717                 NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "callback", "function"));
2718             return result;
2719         }
2720     }
2721     return StoreWebArchiveInternal(env, info, baseName, autoName);
2722 }
2723 
StoreWebArchiveInternal(napi_env env, napi_callback_info info, const std::string &baseName, bool autoName)2724 napi_value NapiWebviewController::StoreWebArchiveInternal(napi_env env, napi_callback_info info,
2725     const std::string &baseName, bool autoName)
2726 {
2727     napi_value thisVar = nullptr;
2728     size_t argc = INTEGER_ONE;
2729     size_t argcPromise = INTEGER_TWO;
2730     size_t argcCallback = INTEGER_THREE;
2731     napi_value argv[INTEGER_THREE] = {0};
2732 
2733     napi_value result = nullptr;
2734     napi_get_undefined(env, &result);
2735     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
2736 
2737     WebviewController *webviewController = nullptr;
2738     napi_unwrap(env, thisVar, (void **)&webviewController);
2739 
2740     if (!webviewController || !webviewController->IsInit()) {
2741         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
2742         return result;
2743     }
2744 
2745     if (argc == argcCallback) {
2746         napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
2747         napi_ref jsCallback = nullptr;
2748         napi_create_reference(env, argv[argcCallback - 1], 1, &jsCallback);
2749 
2750         if (jsCallback) {
2751             webviewController->StoreWebArchiveCallback(baseName, autoName, env, std::move(jsCallback));
2752         }
2753         return result;
2754     } else if (argc == argcPromise) {
2755         napi_deferred deferred = nullptr;
2756         napi_value promise = nullptr;
2757         napi_create_promise(env, &deferred, &promise);
2758         if (promise && deferred) {
2759             webviewController->StoreWebArchivePromise(baseName, autoName, env, deferred);
2760         }
2761         return promise;
2762     }
2763     return result;
2764 }
2765 
GetHitTestValue(napi_env env, napi_callback_info info)2766 napi_value NapiWebviewController::GetHitTestValue(napi_env env, napi_callback_info info)
2767 {
2768     napi_value result = nullptr;
2769     WebviewController *webviewController = GetWebviewController(env, info);
2770     if (!webviewController) {
2771         return nullptr;
2772     }
2773 
2774     std::shared_ptr<HitTestResult> nwebResult = webviewController->GetHitTestValue();
2775 
2776     napi_create_object(env, &result);
2777 
2778     napi_value type;
2779     if (nwebResult) {
2780         napi_create_uint32(env, nwebResult->GetType(), &type);
2781     } else {
2782         napi_create_uint32(env, HitTestResult::UNKNOWN_TYPE, &type);
2783     }
2784     napi_set_named_property(env, result, "type", type);
2785 
2786     napi_value extra;
2787     if (nwebResult) {
2788         napi_create_string_utf8(env, nwebResult->GetExtra().c_str(), NAPI_AUTO_LENGTH, &extra);
2789     } else {
2790         napi_create_string_utf8(env, "", NAPI_AUTO_LENGTH, &extra);
2791     }
2792     napi_set_named_property(env, result, "extra", extra);
2793 
2794     return result;
2795 }
2796 
RequestFocus(napi_env env, napi_callback_info info)2797 napi_value NapiWebviewController::RequestFocus(napi_env env, napi_callback_info info)
2798 {
2799     napi_value result = nullptr;
2800     WebviewController *webviewController = GetWebviewController(env, info);
2801     if (!webviewController) {
2802         return nullptr;
2803     }
2804 
2805     webviewController->RequestFocus();
2806     NAPI_CALL(env, napi_get_undefined(env, &result));
2807     return result;
2808 }
2809 
PostUrl(napi_env env, napi_callback_info info)2810 napi_value NapiWebviewController::PostUrl(napi_env env, napi_callback_info info)
2811 {
2812     WVLOG_D("NapiWebMessageExt::PostUrl start");
2813     napi_value thisVar = nullptr;
2814     napi_value result = nullptr;
2815     size_t argc = INTEGER_TWO;
2816     napi_value argv[INTEGER_TWO] = { 0 };
2817     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
2818     if (argc != INTEGER_TWO) {
2819         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2820             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "two"));
2821         return result;
2822     }
2823 
2824     WebviewController *webviewController = nullptr;
2825     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
2826     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
2827         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
2828         return nullptr;
2829     }
2830 
2831     std::string url;
2832     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], url)) {
2833         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2834             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "url", "string"));
2835         return result;
2836     }
2837 
2838     bool isArrayBuffer = false;
2839     NAPI_CALL(env, napi_is_arraybuffer(env, argv[INTEGER_ONE], &isArrayBuffer));
2840     if (!isArrayBuffer) {
2841         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2842             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "postData", "array"));
2843         return result;
2844     }
2845 
2846     char *arrBuf = nullptr;
2847     size_t byteLength = 0;
2848     napi_get_arraybuffer_info(env, argv[INTEGER_ONE], (void **)&arrBuf, &byteLength);
2849 
2850     std::vector<char> postData(arrBuf, arrBuf + byteLength);
2851     ErrCode ret = webviewController->PostUrl(url, postData);
2852     if (ret != NO_ERROR) {
2853         if (ret == NWEB_ERROR) {
2854             WVLOG_E("PostData failed");
2855             return result;
2856         }
2857         BusinessError::ThrowErrorByErrcode(env, ret);
2858         return result;
2859     }
2860     NAPI_CALL(env, napi_get_undefined(env, &result));
2861     return result;
2862 }
2863 
LoadUrl(napi_env env, napi_callback_info info)2864 napi_value NapiWebviewController::LoadUrl(napi_env env, napi_callback_info info)
2865 {
2866     napi_value thisVar = nullptr;
2867     napi_value result = nullptr;
2868     size_t argc = INTEGER_TWO;
2869     napi_value argv[INTEGER_TWO];
2870     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
2871     if ((argc != INTEGER_ONE) && (argc != INTEGER_TWO)) {
2872         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2873             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_TWO, "one", "two"));
2874         return nullptr;
2875     }
2876     WebviewController *webviewController = nullptr;
2877     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
2878     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
2879         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
2880         return nullptr;
2881     }
2882     napi_valuetype webSrcType;
2883     napi_typeof(env, argv[INTEGER_ZERO], &webSrcType);
2884     if (webSrcType != napi_string && webSrcType != napi_object) {
2885         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2886             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_TYPE_INVALID, "url"));
2887         return nullptr;
2888     }
2889     std::string webSrc;
2890     if (!webviewController->ParseUrl(env, argv[INTEGER_ZERO], webSrc)) {
2891         BusinessError::ThrowErrorByErrcode(env, INVALID_URL);
2892         return nullptr;
2893     }
2894     if (argc == INTEGER_ONE) {
2895         ErrCode ret = webviewController->LoadUrl(webSrc);
2896         if (ret != NO_ERROR) {
2897             if (ret == NWEB_ERROR) {
2898                 return nullptr;
2899             }
2900             BusinessError::ThrowErrorByErrcode(env, ret);
2901             return nullptr;
2902         }
2903         NAPI_CALL(env, napi_get_undefined(env, &result));
2904         return result;
2905     }
2906     return LoadUrlWithHttpHeaders(env, info, webSrc, argv, webviewController);
2907 }
2908 
LoadUrlWithHttpHeaders(napi_env env, napi_callback_info info, const std::string& url, const napi_value* argv, WebviewController* webviewController)2909 napi_value NapiWebviewController::LoadUrlWithHttpHeaders(napi_env env, napi_callback_info info, const std::string& url,
2910     const napi_value* argv, WebviewController* webviewController)
2911 {
2912     napi_value result = nullptr;
2913     std::map<std::string, std::string> httpHeaders;
2914     napi_value array = argv[INTEGER_ONE];
2915     bool isArray = false;
2916     napi_is_array(env, array, &isArray);
2917     if (isArray) {
2918         uint32_t arrayLength = INTEGER_ZERO;
2919         napi_get_array_length(env, array, &arrayLength);
2920         for (uint32_t i = 0; i < arrayLength; ++i) {
2921             std::string key;
2922             std::string value;
2923             napi_value obj = nullptr;
2924             napi_value keyObj = nullptr;
2925             napi_value valueObj = nullptr;
2926             napi_get_element(env, array, i, &obj);
2927             if (napi_get_named_property(env, obj, "headerKey", &keyObj) != napi_ok) {
2928                 continue;
2929             }
2930             if (napi_get_named_property(env, obj, "headerValue", &valueObj) != napi_ok) {
2931                 continue;
2932             }
2933             NapiParseUtils::ParseString(env, keyObj, key);
2934             NapiParseUtils::ParseString(env, valueObj, value);
2935             httpHeaders[key] = value;
2936         }
2937     } else {
2938         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
2939         return nullptr;
2940     }
2941 
2942     ErrCode ret = webviewController->LoadUrl(url, httpHeaders);
2943     if (ret != NO_ERROR) {
2944         if (ret == NWEB_ERROR) {
2945             WVLOG_E("LoadUrl failed.");
2946             return nullptr;
2947         }
2948         BusinessError::ThrowErrorByErrcode(env, ret);
2949         return nullptr;
2950     }
2951     NAPI_CALL(env, napi_get_undefined(env, &result));
2952     return result;
2953 }
2954 
LoadData(napi_env env, napi_callback_info info)2955 napi_value NapiWebviewController::LoadData(napi_env env, napi_callback_info info)
2956 {
2957     napi_value thisVar = nullptr;
2958     napi_value result = nullptr;
2959     size_t argc = INTEGER_FIVE;
2960     napi_value argv[INTEGER_FIVE];
2961     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
2962     if ((argc != INTEGER_THREE) && (argc != INTEGER_FOUR) &&
2963         (argc != INTEGER_FIVE)) {
2964         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
2965             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_TWO, "three", "four"));
2966         return nullptr;
2967     }
2968     WebviewController *webviewController = nullptr;
2969     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
2970     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
2971         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
2972         return nullptr;
2973     }
2974     std::string data;
2975     std::string mimeType;
2976     std::string encoding;
2977     std::string baseUrl;
2978     std::string historyUrl;
2979     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], data) ||
2980         !NapiParseUtils::ParseString(env, argv[INTEGER_ONE], mimeType) ||
2981         !NapiParseUtils::ParseString(env, argv[INTEGER_TWO], encoding)) {
2982         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR, ParamCheckErrorMsgTemplate::TYPE_ALL_STRING);
2983         return nullptr;
2984     }
2985     if ((argc >= INTEGER_FOUR) && !NapiParseUtils::ParseString(env, argv[INTEGER_THREE], baseUrl)) {
2986         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR, ParamCheckErrorMsgTemplate::TYPE_ALL_STRING);
2987         return nullptr;
2988     }
2989     if ((argc == INTEGER_FIVE) && !NapiParseUtils::ParseString(env, argv[INTEGER_FOUR], historyUrl)) {
2990         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR, ParamCheckErrorMsgTemplate::TYPE_ALL_STRING);
2991         return nullptr;
2992     }
2993     ErrCode ret = webviewController->LoadData(data, mimeType, encoding, baseUrl, historyUrl);
2994     if (ret != NO_ERROR) {
2995         if (ret == NWEB_ERROR) {
2996             WVLOG_E("LoadData failed.");
2997             return nullptr;
2998         }
2999         BusinessError::ThrowErrorByErrcode(env, ret);
3000         return nullptr;
3001     }
3002     NAPI_CALL(env, napi_get_undefined(env, &result));
3003     return result;
3004 }
3005 
GetHitTest(napi_env env, napi_callback_info info)3006 napi_value NapiWebviewController::GetHitTest(napi_env env, napi_callback_info info)
3007 {
3008     napi_value result = nullptr;
3009     WebviewController *webviewController = GetWebviewController(env, info);
3010     if (!webviewController) {
3011         return nullptr;
3012     }
3013 
3014     int32_t type = webviewController->GetHitTest();
3015     napi_create_int32(env, type, &result);
3016     return result;
3017 }
3018 
ClearMatches(napi_env env, napi_callback_info info)3019 napi_value NapiWebviewController::ClearMatches(napi_env env, napi_callback_info info)
3020 {
3021     napi_value thisVar = nullptr;
3022     napi_value result = nullptr;
3023 
3024     NAPI_CALL(env, napi_get_undefined(env, &result));
3025     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
3026 
3027     WebviewController *controller = nullptr;
3028     napi_unwrap(env, thisVar, (void **)&controller);
3029     if (!controller || !controller->IsInit()) {
3030         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3031         return result;
3032     }
3033     controller->ClearMatches();
3034     return result;
3035 }
3036 
SearchNext(napi_env env, napi_callback_info info)3037 napi_value NapiWebviewController::SearchNext(napi_env env, napi_callback_info info)
3038 {
3039     napi_value thisVar = nullptr;
3040     napi_value result = nullptr;
3041     size_t argc = INTEGER_ONE;
3042     napi_value argv[INTEGER_ONE] = { 0 };
3043 
3044     NAPI_CALL(env, napi_get_undefined(env, &result));
3045     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3046     if (argc != INTEGER_ONE) {
3047         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3048             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
3049         return result;
3050     }
3051     bool forward;
3052     if (!NapiParseUtils::ParseBoolean(env, argv[0], forward)) {
3053         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3054             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "forward", "boolean"));
3055         return result;
3056     }
3057 
3058     WebviewController *controller = nullptr;
3059     napi_unwrap(env, thisVar, (void **)&controller);
3060     if (!controller || !controller->IsInit()) {
3061         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3062         return result;
3063     }
3064     controller->SearchNext(forward);
3065     return result;
3066 }
3067 
SearchAllAsync(napi_env env, napi_callback_info info)3068 napi_value NapiWebviewController::SearchAllAsync(napi_env env, napi_callback_info info)
3069 {
3070     napi_value thisVar = nullptr;
3071     napi_value result = nullptr;
3072     size_t argc = INTEGER_ONE;
3073     napi_value argv[INTEGER_ONE] = { 0 };
3074 
3075     NAPI_CALL(env, napi_get_undefined(env, &result));
3076     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3077     if (argc != INTEGER_ONE) {
3078         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3079             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
3080         return result;
3081     }
3082     std::string searchString;
3083     if (!NapiParseUtils::ParseString(env, argv[0], searchString)) {
3084         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3085             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "searchString", "number"));
3086         return result;
3087     }
3088 
3089     WebviewController *controller = nullptr;
3090     napi_unwrap(env, thisVar, (void **)&controller);
3091     if (!controller || !controller->IsInit()) {
3092         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3093         return result;
3094     }
3095     controller->SearchAllAsync(searchString);
3096     return result;
3097 }
3098 
ClearSslCache(napi_env env, napi_callback_info info)3099 napi_value NapiWebviewController::ClearSslCache(napi_env env, napi_callback_info info)
3100 {
3101     napi_value thisVar = nullptr;
3102     napi_value result = nullptr;
3103 
3104     NAPI_CALL(env, napi_get_undefined(env, &result));
3105     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
3106 
3107     WebviewController *controller = nullptr;
3108     napi_unwrap(env, thisVar, (void **)&controller);
3109     if (!controller || !controller->IsInit()) {
3110         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3111         return result;
3112     }
3113     controller->ClearSslCache();
3114     return result;
3115 }
3116 
ClearClientAuthenticationCache(napi_env env, napi_callback_info info)3117 napi_value NapiWebviewController::ClearClientAuthenticationCache(napi_env env, napi_callback_info info)
3118 {
3119     napi_value thisVar = nullptr;
3120     napi_value result = nullptr;
3121 
3122     NAPI_CALL(env, napi_get_undefined(env, &result));
3123     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
3124 
3125     WebviewController *controller = nullptr;
3126     napi_unwrap(env, thisVar, (void **)&controller);
3127     if (!controller || !controller->IsInit()) {
3128         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3129         return result;
3130     }
3131     controller->ClearClientAuthenticationCache();
3132 
3133     return result;
3134 }
3135 
Stop(napi_env env, napi_callback_info info)3136 napi_value NapiWebviewController::Stop(napi_env env, napi_callback_info info)
3137 {
3138     napi_value thisVar = nullptr;
3139     napi_value result = nullptr;
3140     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
3141 
3142     WebviewController *controller = nullptr;
3143     napi_unwrap(env, thisVar, (void **)&controller);
3144     if (!controller || !controller->IsInit()) {
3145         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3146         return result;
3147     }
3148     controller->Stop();
3149 
3150     NAPI_CALL(env, napi_get_undefined(env, &result));
3151     return result;
3152 }
3153 
Zoom(napi_env env, napi_callback_info info)3154 napi_value NapiWebviewController::Zoom(napi_env env, napi_callback_info info)
3155 {
3156     napi_value thisVar = nullptr;
3157     napi_value result = nullptr;
3158     size_t argc = INTEGER_ONE;
3159     napi_value argv[INTEGER_ONE] = { 0 };
3160 
3161     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3162     if (argc != INTEGER_ONE) {
3163         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3164             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
3165         return result;
3166     }
3167     float factor = 0.0;
3168     if (!NapiParseUtils::ParseFloat(env, argv[0], factor)) {
3169         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3170             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "factor", "number"));
3171         return result;
3172     }
3173 
3174     WebviewController *controller = nullptr;
3175     napi_unwrap(env, thisVar, (void **)&controller);
3176     if (!controller || !controller->IsInit()) {
3177         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3178         return result;
3179     }
3180 
3181     ErrCode ret = controller->Zoom(factor);
3182     if (ret != NO_ERROR) {
3183         if (ret == NWEB_ERROR) {
3184             WVLOG_E("Zoom failed.");
3185             return result;
3186         }
3187         BusinessError::ThrowErrorByErrcode(env, ret);
3188     }
3189 
3190     NAPI_CALL(env, napi_get_undefined(env, &result));
3191     return result;
3192 }
3193 
InnerCompleteWindowNew(napi_env env, napi_callback_info info)3194 napi_value NapiWebviewController::InnerCompleteWindowNew(napi_env env, napi_callback_info info)
3195 {
3196     napi_value thisVar = nullptr;
3197     size_t argc = INTEGER_ONE;
3198     napi_value argv[INTEGER_ONE];
3199     void* data = nullptr;
3200     napi_get_cb_info(env, info, &argc, argv, &thisVar, &data);
3201 
3202     int32_t parentNwebId = -1;
3203     if (!NapiParseUtils::ParseInt32(env, argv[0], parentNwebId) || parentNwebId == -1) {
3204         WVLOG_E("Parse parent nweb id failed.");
3205         return nullptr;
3206     }
3207     WebviewController* webviewController = nullptr;
3208     napi_status status = napi_unwrap(env, thisVar, (void**)&webviewController);
3209     if ((!webviewController) || (status != napi_ok)) {
3210         WVLOG_E("webviewController is nullptr.");
3211         return nullptr;
3212     }
3213     webviewController->InnerCompleteWindowNew(parentNwebId);
3214     return thisVar;
3215 }
3216 
RegisterJavaScriptProxy(napi_env env, napi_callback_info info)3217 napi_value NapiWebviewController::RegisterJavaScriptProxy(napi_env env, napi_callback_info info)
3218 {
3219     napi_value thisVar = nullptr;
3220     napi_value result = nullptr;
3221     size_t argc = INTEGER_FIVE;
3222     napi_value argv[INTEGER_FIVE] = { 0 };
3223     napi_get_undefined(env, &result);
3224     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3225     if (argc != INTEGER_THREE && argc != INTEGER_FOUR && argc != INTEGER_FIVE) {
3226         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3227             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_THREE, "three", "four", "five"));
3228         return result;
3229     }
3230     napi_valuetype valueType = napi_undefined;
3231     napi_typeof(env, argv[INTEGER_ZERO], &valueType);
3232     if (valueType != napi_object) {
3233         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3234             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "object", "object"));
3235         return result;
3236     }
3237     RegisterJavaScriptProxyParam param;
3238     if (!ParseRegisterJavaScriptProxyParam(env, argc, argv, &param)) {
3239         return result;
3240     }
3241     WebviewController* controller = nullptr;
3242     napi_unwrap(env, thisVar, (void **)&controller);
3243     if (!controller || !controller->IsInit()) {
3244         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3245         return result;
3246     }
3247     controller->SetNWebJavaScriptResultCallBack();
3248     controller->RegisterJavaScriptProxy(param);
3249     return result;
3250 }
3251 
DeleteJavaScriptRegister(napi_env env, napi_callback_info info)3252 napi_value NapiWebviewController::DeleteJavaScriptRegister(napi_env env, napi_callback_info info)
3253 {
3254     napi_value thisVar = nullptr;
3255     napi_value result = nullptr;
3256     size_t argc = INTEGER_ONE;
3257     napi_value argv[INTEGER_ONE] = { 0 };
3258 
3259     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3260     if (argc != INTEGER_ONE) {
3261         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3262             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
3263         return result;
3264     }
3265 
3266     std::string objName;
3267     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], objName)) {
3268         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3269             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "name", "string"));
3270         return result;
3271     }
3272 
3273     WebviewController *controller = nullptr;
3274     napi_unwrap(env, thisVar, (void **)&controller);
3275     if (!controller || !controller->IsInit()) {
3276         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3277         return result;
3278     }
3279     ErrCode ret = controller->DeleteJavaScriptRegister(objName, {});
3280     if (ret != NO_ERROR) {
3281         BusinessError::ThrowErrorByErrcode(env, ret);
3282         return result;
3283     }
3284 
3285     NAPI_CALL(env, napi_get_undefined(env, &result));
3286     return result;
3287 }
3288 
RunJavaScript(napi_env env, napi_callback_info info)3289 napi_value NapiWebviewController::RunJavaScript(napi_env env, napi_callback_info info)
3290 {
3291     return RunJS(env, info, false);
3292 }
3293 
RunJavaScriptExt(napi_env env, napi_callback_info info)3294 napi_value NapiWebviewController::RunJavaScriptExt(napi_env env, napi_callback_info info)
3295 {
3296     return RunJS(env, info, true);
3297 }
3298 
RunJS(napi_env env, napi_callback_info info, bool extention)3299 napi_value NapiWebviewController::RunJS(napi_env env, napi_callback_info info, bool extention)
3300 {
3301     napi_value thisVar = nullptr;
3302     napi_value result = nullptr;
3303     size_t argc = INTEGER_ONE;
3304     size_t argcPromise = INTEGER_ONE;
3305     size_t argcCallback = INTEGER_TWO;
3306     napi_value argv[INTEGER_TWO] = { 0 };
3307 
3308     napi_get_undefined(env, &result);
3309     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3310 
3311     if (argc != argcPromise && argc != argcCallback) {
3312         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3313             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "two"));
3314         return result;
3315     }
3316 
3317     if (argc == argcCallback) {
3318         napi_valuetype valueType = napi_null;
3319         napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3320         napi_typeof(env, argv[argcCallback - 1], &valueType);
3321         if (valueType != napi_function) {
3322             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3323                 NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "callback", "function"));
3324             return result;
3325         }
3326     }
3327 
3328     if (maxFdNum_ == -1) {
3329         maxFdNum_ =
3330             std::atoi(NWebAdapterHelper::Instance().ParsePerfConfig("flowBufferConfig", "maxFdNumber").c_str());
3331     }
3332 
3333     if (usedFd_.load() < maxFdNum_) {
3334         return RunJavaScriptInternalExt(env, info, extention);
3335     }
3336 
3337     std::string script;
3338     napi_valuetype valueType = napi_undefined;
3339     napi_typeof(env, argv[INTEGER_ZERO], &valueType);
3340     bool parseResult = (valueType == napi_string) ? NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], script) :
3341         NapiParseUtils::ParseArrayBuffer(env, argv[INTEGER_ZERO], script);
3342     if (!parseResult) {
3343         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3344             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "script", "string"));
3345         return result;
3346     }
3347     return RunJavaScriptInternal(env, info, script, extention);
3348 }
3349 
RunCreatePDFExt(napi_env env, napi_callback_info info)3350 napi_value NapiWebviewController::RunCreatePDFExt(napi_env env, napi_callback_info info)
3351 {
3352     napi_value thisVar = nullptr;
3353     napi_value result = nullptr;
3354     size_t argc = INTEGER_ONE;
3355     size_t argcPromise = INTEGER_ONE;
3356     size_t argcCallback = INTEGER_TWO;
3357     napi_value argv[INTEGER_TWO] = { 0 };
3358 
3359     napi_get_undefined(env, &result);
3360     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3361 
3362     WebviewController* webviewController = nullptr;
3363     napi_unwrap(env, thisVar, (void**)&webviewController);
3364 
3365     if (!webviewController || !webviewController->IsInit()) {
3366         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3367         return result;
3368     }
3369 
3370     std::shared_ptr<NWebPDFConfigArgs> pdfConfig = ParsePDFConfigArgs(env, argv[INTEGER_ZERO]);
3371     if (pdfConfig == nullptr) {
3372         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
3373         return nullptr;
3374     }
3375 
3376     if (argc == argcCallback) {
3377         napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3378         napi_ref jsCallback = nullptr;
3379         napi_create_reference(env, argv[argcCallback - 1], 1, &jsCallback);
3380 
3381         if (jsCallback) {
3382             webviewController->CreatePDFCallbackExt(env, pdfConfig, std::move(jsCallback));
3383         }
3384         return result;
3385     } else if (argc == argcPromise) {
3386         napi_deferred deferred = nullptr;
3387         napi_value promise = nullptr;
3388         napi_create_promise(env, &deferred, &promise);
3389         if (promise && deferred) {
3390             webviewController->CreatePDFPromiseExt(env, pdfConfig, deferred);
3391         }
3392         return promise;
3393     }
3394     return result;
3395 }
3396 
RunJavaScriptInternal(napi_env env, napi_callback_info info, const std::string &script, bool extention)3397 napi_value NapiWebviewController::RunJavaScriptInternal(napi_env env, napi_callback_info info,
3398     const std::string &script, bool extention)
3399 {
3400     napi_value thisVar = nullptr;
3401     size_t argc = INTEGER_ONE;
3402     size_t argcPromise = INTEGER_ONE;
3403     size_t argcCallback = INTEGER_TWO;
3404     napi_value argv[INTEGER_TWO] = {0};
3405 
3406     napi_value result = nullptr;
3407     napi_get_undefined(env, &result);
3408     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3409 
3410     WebviewController *webviewController = nullptr;
3411     napi_unwrap(env, thisVar, (void **)&webviewController);
3412 
3413     if (!webviewController || !webviewController->IsInit()) {
3414         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3415         return result;
3416     }
3417 
3418     if (argc == argcCallback) {
3419         napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3420         napi_ref jsCallback = nullptr;
3421         napi_create_reference(env, argv[argcCallback - 1], 1, &jsCallback);
3422 
3423         if (jsCallback) {
3424             webviewController->RunJavaScriptCallback(script, env, std::move(jsCallback), extention);
3425         }
3426         return result;
3427     } else if (argc == argcPromise) {
3428         napi_deferred deferred = nullptr;
3429         napi_value promise = nullptr;
3430         napi_create_promise(env, &deferred, &promise);
3431         if (promise && deferred) {
3432             webviewController->RunJavaScriptPromise(script, env, deferred, extention);
3433         }
3434         return promise;
3435     }
3436     return result;
3437 }
3438 
ConstructFlowbuf(napi_env env, napi_value argv, int& fd, size_t& scriptLength)3439 ErrCode NapiWebviewController::ConstructFlowbuf(napi_env env, napi_value argv, int& fd, size_t& scriptLength)
3440 {
3441     auto flowbufferAdapter = OhosAdapterHelper::GetInstance().CreateFlowbufferAdapter();
3442     if (!flowbufferAdapter) {
3443         return NWebError::NEW_OOM;
3444     }
3445     flowbufferAdapter->StartPerformanceBoost();
3446 
3447     napi_valuetype valueType = napi_undefined;
3448     napi_typeof(env, argv, &valueType);
3449 
3450     ErrCode constructResult = (valueType == napi_string) ?
3451         NapiParseUtils::ConstructStringFlowbuf(env, argv, fd, scriptLength) :
3452         NapiParseUtils::ConstructArrayBufFlowbuf(env, argv, fd, scriptLength);
3453     return constructResult;
3454 }
3455 
RunJSBackToOriginal(napi_env env, napi_callback_info info, bool extention, napi_value argv, napi_value result)3456 napi_value NapiWebviewController::RunJSBackToOriginal(napi_env env, napi_callback_info info,
3457     bool extention, napi_value argv, napi_value result)
3458 {
3459     std::string script;
3460     napi_valuetype valueType = napi_undefined;
3461     napi_typeof(env, argv, &valueType);
3462     bool parseResult = (valueType == napi_string) ? NapiParseUtils::ParseString(env, argv, script) :
3463         NapiParseUtils::ParseArrayBuffer(env, argv, script);
3464     if (!parseResult) {
3465         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
3466         return result;
3467     }
3468     return RunJavaScriptInternal(env, info, script, extention);
3469 }
3470 
RunJavaScriptInternalExt(napi_env env, napi_callback_info info, bool extention)3471 napi_value NapiWebviewController::RunJavaScriptInternalExt(napi_env env, napi_callback_info info, bool extention)
3472 {
3473     napi_value thisVar = nullptr;
3474     napi_value result = nullptr;
3475     size_t argc = INTEGER_ONE;
3476     size_t argcPromise = INTEGER_ONE;
3477     size_t argcCallback = INTEGER_TWO;
3478     napi_value argv[INTEGER_TWO] = {0};
3479 
3480     napi_get_undefined(env, &result);
3481     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3482 
3483     int fd;
3484     size_t scriptLength;
3485     ErrCode constructResult = ConstructFlowbuf(env, argv[INTEGER_ZERO], fd, scriptLength);
3486     if (constructResult != NO_ERROR) {
3487         return RunJSBackToOriginal(env, info, extention, argv[INTEGER_ZERO], result);
3488     }
3489     usedFd_++;
3490 
3491     WebviewController *webviewController = nullptr;
3492     napi_unwrap(env, thisVar, (void **)&webviewController);
3493 
3494     if (!webviewController || !webviewController->IsInit()) {
3495         close(fd);
3496         usedFd_--;
3497         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3498         return result;
3499     }
3500 
3501     if (argc == argcCallback) {
3502         napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3503         napi_ref jsCallback = nullptr;
3504         napi_create_reference(env, argv[argcCallback - 1], 1, &jsCallback);
3505 
3506         if (jsCallback) {
3507             // RunJavaScriptCallbackExt will close fd after IPC
3508             webviewController->RunJavaScriptCallbackExt(fd, scriptLength, env, std::move(jsCallback), extention);
3509         }
3510         usedFd_--;
3511         return result;
3512     } else if (argc == argcPromise) {
3513         napi_deferred deferred = nullptr;
3514         napi_value promise = nullptr;
3515         napi_create_promise(env, &deferred, &promise);
3516         if (promise && deferred) {
3517             // RunJavaScriptCallbackExt will close fd after IPC
3518             webviewController->RunJavaScriptPromiseExt(fd, scriptLength, env, deferred, extention);
3519         }
3520         usedFd_--;
3521         return promise;
3522     }
3523     close(fd);
3524     usedFd_--;
3525     return result;
3526 }
3527 
GetUrl(napi_env env, napi_callback_info info)3528 napi_value NapiWebviewController::GetUrl(napi_env env, napi_callback_info info)
3529 {
3530     napi_value result = nullptr;
3531     WebviewController *webviewController = GetWebviewController(env, info);
3532     if (!webviewController) {
3533         return nullptr;
3534     }
3535 
3536     std::string url = "";
3537     url = webviewController->GetUrl();
3538     napi_create_string_utf8(env, url.c_str(), url.length(), &result);
3539 
3540     return result;
3541 }
3542 
GetOriginalUrl(napi_env env, napi_callback_info info)3543 napi_value NapiWebviewController::GetOriginalUrl(napi_env env, napi_callback_info info)
3544 {
3545     napi_value result = nullptr;
3546     WebviewController *webviewController = GetWebviewController(env, info);
3547     if (!webviewController) {
3548         return nullptr;
3549     }
3550 
3551     std::string url = "";
3552     url = webviewController->GetOriginalUrl();
3553     napi_create_string_utf8(env, url.c_str(), url.length(), &result);
3554     return result;
3555 }
3556 
TerminateRenderProcess(napi_env env, napi_callback_info info)3557 napi_value NapiWebviewController::TerminateRenderProcess(napi_env env, napi_callback_info info)
3558 {
3559     napi_value result = nullptr;
3560     WebviewController *webviewController = GetWebviewController(env, info);
3561     if (!webviewController) {
3562         return nullptr;
3563     }
3564     bool ret = false;
3565     ret = webviewController->TerminateRenderProcess();
3566     NAPI_CALL(env, napi_get_boolean(env, ret, &result));
3567     return result;
3568 }
3569 
SetNetworkAvailable(napi_env env, napi_callback_info info)3570 napi_value NapiWebviewController::SetNetworkAvailable(napi_env env, napi_callback_info info)
3571 {
3572     napi_value thisVar = nullptr;
3573     napi_value result = nullptr;
3574     size_t argc = INTEGER_ONE;
3575     napi_value argv[INTEGER_ONE] = { 0 };
3576     bool enable;
3577 
3578     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3579     if (argc != INTEGER_ONE) {
3580         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3581             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
3582         return result;
3583     }
3584 
3585     if (!NapiParseUtils::ParseBoolean(env, argv[0], enable)) {
3586         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3587             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "enable", "booleane"));
3588         return result;
3589     }
3590 
3591     WebviewController *webviewController = nullptr;
3592     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
3593     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
3594         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3595         return nullptr;
3596     }
3597     webviewController->PutNetworkAvailable(enable);
3598     return result;
3599 }
3600 
InnerGetWebId(napi_env env, napi_callback_info info)3601 napi_value NapiWebviewController::InnerGetWebId(napi_env env, napi_callback_info info)
3602 {
3603     napi_value thisVar = nullptr;
3604     napi_value result = nullptr;
3605     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
3606 
3607     WebviewController *webviewController = nullptr;
3608     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
3609     int32_t webId = -1;
3610     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
3611         WVLOG_E("Init error. The WebviewController must be associated with a Web component.");
3612         napi_create_int32(env, webId, &result);
3613         return result;
3614     }
3615 
3616     webId = webviewController->GetWebId();
3617     napi_create_int32(env, webId, &result);
3618 
3619     return result;
3620 }
3621 
HasImage(napi_env env, napi_callback_info info)3622 napi_value NapiWebviewController::HasImage(napi_env env, napi_callback_info info)
3623 {
3624     napi_value thisVar = nullptr;
3625     napi_value result = nullptr;
3626     size_t argc = INTEGER_ONE;
3627     size_t argcPromiseParaNum = INTEGER_ZERO;
3628     size_t argcCallbackParaNum = INTEGER_ONE;
3629     napi_value argv[INTEGER_ONE] = { 0 };
3630 
3631     napi_get_undefined(env, &result);
3632     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3633 
3634     if (argc != argcPromiseParaNum && argc != argcCallbackParaNum) {
3635         NWebError::BusinessError::ThrowErrorByErrcode(env, NWebError::PARAM_CHECK_ERROR,
3636             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_TWO, "zero", "one"));
3637         return result;
3638     }
3639 
3640     if (argc == argcCallbackParaNum) {
3641         napi_valuetype valueType = napi_null;
3642         napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3643         napi_typeof(env, argv[argcCallbackParaNum - 1], &valueType);
3644         if (valueType != napi_function) {
3645             NWebError::BusinessError::ThrowErrorByErrcode(env, NWebError::PARAM_CHECK_ERROR,
3646                 NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "callback", "function"));
3647             return result;
3648         }
3649     }
3650     return HasImageInternal(env, info);
3651 }
3652 
HasImageInternal(napi_env env, napi_callback_info info)3653 napi_value NapiWebviewController::HasImageInternal(napi_env env, napi_callback_info info)
3654 {
3655     napi_value thisVar = nullptr;
3656     size_t argc = INTEGER_ONE;
3657     size_t argcPromiseParaNum = INTEGER_ZERO;
3658     size_t argcCallbackParaNum = INTEGER_ONE;
3659     napi_value argv[INTEGER_ONE] = { 0 };
3660 
3661     napi_value result = nullptr;
3662     napi_get_undefined(env, &result);
3663     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3664 
3665     WebviewController *webviewController = nullptr;
3666     napi_unwrap(env, thisVar, (void **)&webviewController);
3667 
3668     if (!webviewController || !webviewController->IsInit()) {
3669         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3670         return result;
3671     }
3672 
3673     if (argc == argcCallbackParaNum) {
3674         napi_ref jsCallback = nullptr;
3675         napi_create_reference(env, argv[argcCallbackParaNum - 1], 1, &jsCallback);
3676 
3677         if (jsCallback) {
3678             ErrCode ret = webviewController->HasImagesCallback(env, std::move(jsCallback));
3679             if (ret == NWEB_ERROR) {
3680                 return nullptr;
3681             } else if (ret != NO_ERROR) {
3682                 BusinessError::ThrowErrorByErrcode(env, ret);
3683                 return nullptr;
3684             }
3685         }
3686         return result;
3687     } else if (argc == argcPromiseParaNum) {
3688         napi_deferred deferred = nullptr;
3689         napi_value promise = nullptr;
3690         napi_create_promise(env, &deferred, &promise);
3691         if (promise && deferred) {
3692             ErrCode ret = webviewController->HasImagesPromise(env, deferred);
3693             if (ret == NWEB_ERROR) {
3694                 return nullptr;
3695             } else if (ret != NO_ERROR) {
3696                 BusinessError::ThrowErrorByErrcode(env, ret);
3697                 return nullptr;
3698             }
3699         }
3700         return promise;
3701     }
3702     return result;
3703 }
3704 
RemoveCache(napi_env env, napi_callback_info info)3705 napi_value NapiWebviewController::RemoveCache(napi_env env, napi_callback_info info)
3706 {
3707     napi_value thisVar = nullptr;
3708     napi_value result = nullptr;
3709     size_t argc = INTEGER_ONE;
3710     napi_value argv[INTEGER_ONE] = { 0 };
3711     bool includeDiskFiles;
3712 
3713     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
3714     if (argc != INTEGER_ONE) {
3715         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3716             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
3717         return result;
3718     }
3719 
3720     if (!NapiParseUtils::ParseBoolean(env, argv[0], includeDiskFiles)) {
3721         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3722             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "clearRom", "boolean"));
3723         return result;
3724     }
3725 
3726     WebviewController *webviewController = nullptr;
3727     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
3728     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
3729         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3730         return nullptr;
3731     }
3732     webviewController->RemoveCache(includeDiskFiles);
3733     return result;
3734 }
3735 
IsIncognitoMode(napi_env env, napi_callback_info info)3736 napi_value NapiWebviewController::IsIncognitoMode(napi_env env, napi_callback_info info)
3737 {
3738     napi_value result = nullptr;
3739     WebviewController *webviewController = GetWebviewController(env, info);
3740     if (!webviewController) {
3741         return nullptr;
3742     }
3743 
3744     bool incognitoMode = false;
3745     incognitoMode = webviewController->IsIncognitoMode();
3746     NAPI_CALL(env, napi_get_boolean(env, incognitoMode, &result));
3747     return result;
3748 }
3749 
JsConstructor(napi_env env, napi_callback_info info)3750 napi_value NapiWebHistoryList::JsConstructor(napi_env env, napi_callback_info info)
3751 {
3752     napi_value thisVar = nullptr;
3753     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
3754     return thisVar;
3755 }
3756 
getColorType(ImageColorType colorType)3757 Media::PixelFormat getColorType(ImageColorType colorType)
3758 {
3759     Media::PixelFormat pixelFormat_;
3760     switch (colorType) {
3761         case ImageColorType::COLOR_TYPE_UNKNOWN:
3762             pixelFormat_ = Media::PixelFormat::UNKNOWN;
3763             break;
3764         case ImageColorType::COLOR_TYPE_RGBA_8888:
3765             pixelFormat_ = Media::PixelFormat::RGBA_8888;
3766             break;
3767         case ImageColorType::COLOR_TYPE_BGRA_8888:
3768             pixelFormat_ = Media::PixelFormat::BGRA_8888;
3769             break;
3770         default:
3771             pixelFormat_ = Media::PixelFormat::UNKNOWN;
3772             break;
3773     }
3774     return pixelFormat_;
3775 }
3776 
getAlphaType(ImageAlphaType alphaType)3777 Media::AlphaType getAlphaType(ImageAlphaType alphaType)
3778 {
3779     Media::AlphaType alphaType_;
3780     switch (alphaType) {
3781         case ImageAlphaType::ALPHA_TYPE_UNKNOWN:
3782             alphaType_ = Media::AlphaType::IMAGE_ALPHA_TYPE_UNKNOWN;
3783             break;
3784         case ImageAlphaType::ALPHA_TYPE_OPAQUE:
3785             alphaType_ = Media::AlphaType::IMAGE_ALPHA_TYPE_OPAQUE;
3786             break;
3787         case ImageAlphaType::ALPHA_TYPE_PREMULTIPLIED:
3788             alphaType_ = Media::AlphaType::IMAGE_ALPHA_TYPE_PREMUL;
3789             break;
3790         case ImageAlphaType::ALPHA_TYPE_POSTMULTIPLIED:
3791             alphaType_ = Media::AlphaType::IMAGE_ALPHA_TYPE_UNPREMUL;
3792             break;
3793         default:
3794             alphaType_ = Media::AlphaType::IMAGE_ALPHA_TYPE_UNKNOWN;
3795             break;
3796     }
3797     return alphaType_;
3798 }
3799 
GetFavicon(napi_env env, std::shared_ptr<NWebHistoryItem> item)3800 napi_value NapiWebHistoryList::GetFavicon(napi_env env, std::shared_ptr<NWebHistoryItem> item)
3801 {
3802     napi_value result = nullptr;
3803     void *data = nullptr;
3804     int32_t width = 0;
3805     int32_t height = 0;
3806     ImageColorType colorType = ImageColorType::COLOR_TYPE_UNKNOWN;
3807     ImageAlphaType alphaType = ImageAlphaType::ALPHA_TYPE_UNKNOWN;
3808     bool isGetFavicon = item->GetFavicon(&data, width, height, colorType, alphaType);
3809     napi_get_null(env, &result);
3810 
3811     if (!isGetFavicon) {
3812         return result;
3813     }
3814 
3815     Media::InitializationOptions opt;
3816     opt.size.width = width;
3817     opt.size.height = height;
3818     opt.pixelFormat = getColorType(colorType);
3819     opt.alphaType = getAlphaType(alphaType);
3820     opt.editable = true;
3821     auto pixelMap = Media::PixelMap::Create(opt);
3822     if (pixelMap == nullptr) {
3823         return result;
3824     }
3825     uint64_t stride = static_cast<uint64_t>(width) << 2;
3826     uint64_t bufferSize = stride * static_cast<uint64_t>(height);
3827     pixelMap->WritePixels(static_cast<const uint8_t *>(data), bufferSize);
3828     std::shared_ptr<Media::PixelMap> pixelMapToJs(pixelMap.release());
3829     napi_value jsPixelMap = OHOS::Media::PixelMapNapi::CreatePixelMap(env, pixelMapToJs);
3830     return jsPixelMap;
3831 }
3832 
GetItem(napi_env env, napi_callback_info info)3833 napi_value NapiWebHistoryList::GetItem(napi_env env, napi_callback_info info)
3834 {
3835     napi_value thisVar = nullptr;
3836     napi_value result = nullptr;
3837     size_t argc = INTEGER_ONE;
3838     napi_value argv[INTEGER_ONE] = { 0 };
3839     int32_t index;
3840     WebHistoryList *historyList = nullptr;
3841 
3842     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
3843     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&historyList));
3844     if (historyList == nullptr) {
3845         WVLOG_E("unwrap historyList failed.");
3846         return result;
3847     }
3848     if (argc != INTEGER_ONE) {
3849         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3850             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
3851         return result;
3852     }
3853     if (!NapiParseUtils::ParseInt32(env, argv[0], index)) {
3854         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3855             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NOT_NULL_TWO, "index", "int"));
3856         return result;
3857     }
3858     if (index >= historyList->GetListSize() || index < 0) {
3859         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
3860             "BusinessError 401: Parameter error. The value of index must be greater than or equal to 0");
3861         return result;
3862     }
3863 
3864     std::shared_ptr<NWebHistoryItem> item = historyList->GetItem(index);
3865     if (!item) {
3866         return result;
3867     }
3868 
3869     napi_create_object(env, &result);
3870     std::string historyUrl = item->GetHistoryUrl();
3871     std::string historyRawUrl = item->GetHistoryRawUrl();
3872     std::string title = item->GetHistoryTitle();
3873 
3874     napi_value js_historyUrl;
3875     napi_create_string_utf8(env, historyUrl.c_str(), historyUrl.length(), &js_historyUrl);
3876     napi_set_named_property(env, result, "historyUrl", js_historyUrl);
3877 
3878     napi_value js_historyRawUrl;
3879     napi_create_string_utf8(env, historyRawUrl.c_str(), historyRawUrl.length(), &js_historyRawUrl);
3880     napi_set_named_property(env, result, "historyRawUrl", js_historyRawUrl);
3881 
3882     napi_value js_title;
3883     napi_create_string_utf8(env, title.c_str(), title.length(), &js_title);
3884     napi_set_named_property(env, result, "title", js_title);
3885 
3886     napi_value js_icon = GetFavicon(env, item);
3887     napi_set_named_property(env, result, "icon", js_icon);
3888     return result;
3889 }
3890 
getBackForwardEntries(napi_env env, napi_callback_info info)3891 napi_value NapiWebviewController::getBackForwardEntries(napi_env env, napi_callback_info info)
3892 {
3893     napi_value thisVar = nullptr;
3894     napi_value result = nullptr;
3895     WebviewController *webviewController = nullptr;
3896 
3897     NAPI_CALL(env, napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr));
3898     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webviewController));
3899     if (webviewController == nullptr || !webviewController->IsInit()) {
3900         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3901         return nullptr;
3902     }
3903 
3904     std::shared_ptr<NWebHistoryList> list = webviewController->GetHistoryList();
3905     if (!list) {
3906         return result;
3907     }
3908 
3909     int32_t currentIndex = list->GetCurrentIndex();
3910     int32_t size = list->GetListSize();
3911 
3912     napi_value historyList = nullptr;
3913     NAPI_CALL(env, napi_get_reference_value(env, g_historyListRef, &historyList));
3914     NAPI_CALL(env, napi_new_instance(env, historyList, 0, NULL, &result));
3915 
3916     napi_value js_currentIndex;
3917     napi_create_int32(env, currentIndex, &js_currentIndex);
3918     napi_set_named_property(env, result, "currentIndex", js_currentIndex);
3919 
3920     napi_value js_size;
3921     napi_create_int32(env, size, &js_size);
3922     napi_set_named_property(env, result, "size", js_size);
3923 
3924     WebHistoryList *webHistoryList = new (std::nothrow) WebHistoryList(list);
3925     if (webHistoryList == nullptr) {
3926         return result;
3927     }
3928 
3929     NAPI_CALL(env, napi_wrap(env, result, webHistoryList,
3930         [](napi_env env, void *data, void *hint) {
3931             WebHistoryList *webHistoryList = static_cast<WebHistoryList *>(data);
3932             delete webHistoryList;
3933         },
3934         nullptr, nullptr));
3935 
3936     return result;
3937 }
3938 
GetFavicon(napi_env env, napi_callback_info info)3939 napi_value NapiWebviewController::GetFavicon(napi_env env, napi_callback_info info)
3940 {
3941     napi_value thisVar = nullptr;
3942     napi_value result = nullptr;
3943     napi_get_null(env, &result);
3944     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
3945 
3946     WebviewController *webviewController = nullptr;
3947     napi_unwrap(env, thisVar, (void **)&webviewController);
3948 
3949     if (!webviewController || !webviewController->IsInit()) {
3950         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3951         return result;
3952     }
3953 
3954     const void *data = nullptr;
3955     size_t width = 0;
3956     size_t height = 0;
3957     ImageColorType colorType = ImageColorType::COLOR_TYPE_UNKNOWN;
3958     ImageAlphaType alphaType = ImageAlphaType::ALPHA_TYPE_UNKNOWN;
3959     bool isGetFavicon = webviewController->GetFavicon(&data, width, height, colorType, alphaType);
3960     if (!isGetFavicon) {
3961         return result;
3962     }
3963 
3964     Media::InitializationOptions opt;
3965     opt.size.width = static_cast<int32_t>(width);
3966     opt.size.height = static_cast<int32_t>(height);
3967     opt.pixelFormat = getColorType(colorType);
3968     opt.alphaType = getAlphaType(alphaType);
3969     opt.editable = true;
3970     auto pixelMap = Media::PixelMap::Create(opt);
3971     if (pixelMap == nullptr) {
3972         return result;
3973     }
3974     uint64_t stride = static_cast<uint64_t>(width) << 2;
3975     uint64_t bufferSize = stride * static_cast<uint64_t>(height);
3976     pixelMap->WritePixels(static_cast<const uint8_t *>(data), bufferSize);
3977     std::shared_ptr<Media::PixelMap> pixelMapToJs(pixelMap.release());
3978     napi_value jsPixelMap = OHOS::Media::PixelMapNapi::CreatePixelMap(env, pixelMapToJs);
3979     return jsPixelMap;
3980 }
3981 
SerializeWebState(napi_env env, napi_callback_info info)3982 napi_value NapiWebviewController::SerializeWebState(napi_env env, napi_callback_info info)
3983 {
3984     napi_value thisVar = nullptr;
3985     napi_value result = nullptr;
3986     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
3987     napi_get_null(env, &result);
3988 
3989     WebviewController *webviewController = nullptr;
3990     napi_unwrap(env, thisVar, (void **)&webviewController);
3991     if (!webviewController || !webviewController->IsInit()) {
3992         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
3993         return result;
3994     }
3995 
3996     void *data = nullptr;
3997     napi_value buffer = nullptr;
3998     auto webState = webviewController->SerializeWebState();
3999 
4000     NAPI_CALL(env, napi_create_arraybuffer(env, webState.size(), &data, &buffer));
4001     int retCode = memcpy_s(data, webState.size(), webState.data(), webState.size());
4002     if (retCode != 0) {
4003         return result;
4004     }
4005     NAPI_CALL(env, napi_create_typedarray(env, napi_uint8_array, webState.size(), buffer, 0, &result));
4006     return result;
4007 }
4008 
RestoreWebState(napi_env env, napi_callback_info info)4009 napi_value NapiWebviewController::RestoreWebState(napi_env env, napi_callback_info info)
4010 {
4011     napi_value thisVar = nullptr;
4012     napi_value result = nullptr;
4013     size_t argc = INTEGER_ONE;
4014     napi_value argv[INTEGER_ONE] = { 0 };
4015     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
4016     napi_get_null(env, &result);
4017 
4018     WebviewController *webviewController = nullptr;
4019     napi_unwrap(env, thisVar, (void **)&webviewController);
4020     if (!webviewController || !webviewController->IsInit()) {
4021         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4022         return result;
4023     }
4024 
4025     bool isTypedArray = false;
4026     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4027     if (argc != INTEGER_ONE) {
4028         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4029             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
4030         return result;
4031     }
4032     NAPI_CALL(env, napi_is_typedarray(env, argv[0], &isTypedArray));
4033     if (!isTypedArray) {
4034         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4035             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "state", "uint8Array"));
4036         return result;
4037     }
4038 
4039     napi_typedarray_type type;
4040     size_t length = 0;
4041     napi_value buffer = nullptr;
4042     size_t offset = 0;
4043     NAPI_CALL(env, napi_get_typedarray_info(env, argv[0], &type, &length, nullptr, &buffer, &offset));
4044     if (type != napi_uint8_array) {
4045         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4046             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "state", "uint8Array"));
4047         return result;
4048     }
4049     uint8_t *data = nullptr;
4050     size_t total = 0;
4051     NAPI_CALL(env, napi_get_arraybuffer_info(env, buffer, reinterpret_cast<void **>(&data), &total));
4052     length = std::min<size_t>(length, total - offset);
4053     std::vector<uint8_t> state(length);
4054     int retCode = memcpy_s(state.data(), state.size(), &data[offset], length);
4055     if (retCode != 0) {
4056         return result;
4057     }
4058     webviewController->RestoreWebState(state);
4059     return result;
4060 }
4061 
ScrollPageDown(napi_env env, napi_callback_info info)4062 napi_value NapiWebviewController::ScrollPageDown(napi_env env, napi_callback_info info)
4063 {
4064     napi_value thisVar = nullptr;
4065     napi_value result = nullptr;
4066     size_t argc = INTEGER_ONE;
4067     napi_value argv[INTEGER_ONE] = { 0 };
4068     bool bottom;
4069 
4070     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4071     if (argc != INTEGER_ONE) {
4072         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4073             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
4074         return result;
4075     }
4076 
4077     if (!NapiParseUtils::ParseBoolean(env, argv[0], bottom)) {
4078         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4079             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "bottom", "booleane"));
4080         return result;
4081     }
4082 
4083     WebviewController *webviewController = nullptr;
4084     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
4085     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
4086         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4087         return nullptr;
4088     }
4089     webviewController->ScrollPageDown(bottom);
4090     return result;
4091 }
4092 
ScrollPageUp(napi_env env, napi_callback_info info)4093 napi_value NapiWebviewController::ScrollPageUp(napi_env env, napi_callback_info info)
4094 {
4095     napi_value thisVar = nullptr;
4096     napi_value result = nullptr;
4097     size_t argc = INTEGER_ONE;
4098     napi_value argv[INTEGER_ONE] = { 0 };
4099     bool top;
4100 
4101     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4102     if (argc != INTEGER_ONE) {
4103         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4104             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
4105         return result;
4106     }
4107 
4108     if (!NapiParseUtils::ParseBoolean(env, argv[0], top)) {
4109         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4110             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "top", "booleane"));
4111         return result;
4112     }
4113 
4114     WebviewController *webviewController = nullptr;
4115     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
4116     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
4117         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4118         return nullptr;
4119     }
4120     webviewController->ScrollPageUp(top);
4121     return result;
4122 }
4123 
CheckSchemeName(const std::string& schemeName)4124 bool CheckSchemeName(const std::string& schemeName)
4125 {
4126     if (schemeName.empty() || schemeName.size() > MAX_CUSTOM_SCHEME_NAME_LENGTH) {
4127         WVLOG_E("Invalid scheme name length");
4128         return false;
4129     }
4130     for (auto it = schemeName.begin(); it != schemeName.end(); it++) {
4131         char chr = *it;
4132         if (!((chr >= 'a' && chr <= 'z') || (chr >= '0' && chr <= '9') ||
4133             (chr == '.') || (chr == '+') || (chr == '-'))) {
4134             WVLOG_E("invalid character %{public}c", chr);
4135             return false;
4136         }
4137     }
4138     return true;
4139 }
4140 
SetCustomizeSchemeOption(Scheme& scheme)4141 void SetCustomizeSchemeOption(Scheme& scheme)
4142 {
4143     std::map<int, std::function<bool(const Scheme&)>> schemeProperties = {
4144         {0, [](const Scheme& scheme) { return scheme.isStandard; }},
4145         {1, [](const Scheme& scheme) { return scheme.isLocal; }},
4146         {2, [](const Scheme& scheme) { return scheme.isDisplayIsolated; }},
4147         {3, [](const Scheme& scheme) { return scheme.isSecure; }},
4148         {4, [](const Scheme& scheme) { return scheme.isSupportCORS; }},
4149         {5, [](const Scheme& scheme) { return scheme.isCspBypassing; }},
4150         {6, [](const Scheme& scheme) { return scheme.isSupportFetch; }},
4151         {7, [](const Scheme& scheme) { return scheme.isCodeCacheSupported; }}
4152     };
4153 
4154     for (const auto& property : schemeProperties) {
4155         if (property.second(scheme)) {
4156             scheme.option += 1 << property.first;
4157         }
4158     }
4159 }
4160 
SetCustomizeScheme(napi_env env, napi_value obj, Scheme& scheme)4161 bool SetCustomizeScheme(napi_env env, napi_value obj, Scheme& scheme)
4162 {
4163     std::map<std::string, std::function<void(Scheme&, bool)>> schemeBooleanProperties = {
4164         {"isSupportCORS", [](Scheme& scheme, bool value) { scheme.isSupportCORS = value; }},
4165         {"isSupportFetch", [](Scheme& scheme, bool value) { scheme.isSupportFetch = value; }},
4166         {"isStandard", [](Scheme& scheme, bool value) { scheme.isStandard = value; }},
4167         {"isLocal", [](Scheme& scheme, bool value) { scheme.isLocal = value; }},
4168         {"isDisplayIsolated", [](Scheme& scheme, bool value) { scheme.isDisplayIsolated = value; }},
4169         {"isSecure", [](Scheme& scheme, bool value) { scheme.isSecure = value; }},
4170         {"isCspBypassing", [](Scheme& scheme, bool value) { scheme.isCspBypassing = value; }},
4171         {"isCodeCacheSupported", [](Scheme& scheme, bool value) { scheme.isCodeCacheSupported = value; }}
4172     };
4173 
4174     for (const auto& property : schemeBooleanProperties) {
4175         napi_value propertyObj = nullptr;
4176         napi_get_named_property(env, obj, property.first.c_str(), &propertyObj);
4177         bool schemeProperty = false;
4178         if (!NapiParseUtils::ParseBoolean(env, propertyObj, schemeProperty)) {
4179             if (property.first == "isSupportCORS" || property.first == "isSupportFetch") {
4180                 return false;
4181             }
4182         }
4183         property.second(scheme, schemeProperty);
4184     }
4185 
4186     napi_value schemeNameObj = nullptr;
4187     if (napi_get_named_property(env, obj, "schemeName", &schemeNameObj) != napi_ok) {
4188         return false;
4189     }
4190     if (!NapiParseUtils::ParseString(env, schemeNameObj, scheme.name)) {
4191         return false;
4192     }
4193 
4194     if (!CheckSchemeName(scheme.name)) {
4195         return false;
4196     }
4197 
4198     SetCustomizeSchemeOption(scheme);
4199     return true;
4200 }
4201 
CustomizeSchemesArrayDataHandler(napi_env env, napi_value array)4202 int32_t CustomizeSchemesArrayDataHandler(napi_env env, napi_value array)
4203 {
4204     uint32_t arrayLength = 0;
4205     napi_get_array_length(env, array, &arrayLength);
4206     if (arrayLength > MAX_CUSTOM_SCHEME_SIZE) {
4207         return PARAM_CHECK_ERROR;
4208     }
4209     std::vector<Scheme> schemeVector;
4210     for (uint32_t i = 0; i < arrayLength; ++i) {
4211         napi_value obj = nullptr;
4212         napi_get_element(env, array, i, &obj);
4213         Scheme scheme;
4214         bool result = SetCustomizeScheme(env, obj, scheme);
4215         if (!result) {
4216             return PARAM_CHECK_ERROR;
4217         }
4218         schemeVector.push_back(scheme);
4219     }
4220     int32_t registerResult;
4221     for (auto it = schemeVector.begin(); it != schemeVector.end(); ++it) {
4222         registerResult = OH_ArkWeb_RegisterCustomSchemes(it->name.c_str(), it->option);
4223         if (registerResult != NO_ERROR) {
4224             return registerResult;
4225         }
4226     }
4227     return NO_ERROR;
4228 }
4229 
CustomizeSchemes(napi_env env, napi_callback_info info)4230 napi_value NapiWebviewController::CustomizeSchemes(napi_env env, napi_callback_info info)
4231 {
4232     if (WebviewController::existNweb_) {
4233         WVLOG_E("There exist web component which has been already created.");
4234     }
4235 
4236     napi_value result = nullptr;
4237     napi_value thisVar = nullptr;
4238     size_t argc = INTEGER_ONE;
4239     napi_value argv[INTEGER_ONE];
4240     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4241     if (argc != INTEGER_ONE) {
4242         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4243             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
4244         return nullptr;
4245     }
4246     napi_value array = argv[INTEGER_ZERO];
4247     bool isArray = false;
4248     napi_is_array(env, array, &isArray);
4249     if (!isArray) {
4250         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4251             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "schemes", "array"));
4252         return nullptr;
4253     }
4254     int32_t registerResult = CustomizeSchemesArrayDataHandler(env, array);
4255     if (registerResult == NO_ERROR) {
4256         NAPI_CALL(env, napi_get_undefined(env, &result));
4257         return result;
4258     }
4259     if (registerResult == PARAM_CHECK_ERROR) {
4260         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4261             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "schemeName", "string"));
4262         return nullptr;
4263     }
4264     BusinessError::ThrowErrorByErrcode(env, REGISTER_CUSTOM_SCHEME_FAILED);
4265     return nullptr;
4266 }
4267 
ScrollTo(napi_env env, napi_callback_info info)4268 napi_value NapiWebviewController::ScrollTo(napi_env env, napi_callback_info info)
4269 {
4270     napi_value thisVar = nullptr;
4271     napi_value result = nullptr;
4272     size_t argc = INTEGER_THREE;
4273     napi_value argv[INTEGER_THREE] = { 0 };
4274     float x;
4275     float y;
4276     int32_t duration;
4277 
4278     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4279     if (argc != INTEGER_TWO && argc != INTEGER_THREE) {
4280         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4281             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_TWO, "two", "three"));
4282         return result;
4283     }
4284 
4285     if (!NapiParseUtils::ParseFloat(env, argv[INTEGER_ZERO], x)) {
4286         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4287             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "x", "number"));
4288         return result;
4289     }
4290 
4291     if (!NapiParseUtils::ParseFloat(env, argv[INTEGER_ONE], y)) {
4292         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4293             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "y", "number"));
4294         return result;
4295     }
4296 
4297     if (argc == INTEGER_THREE) {
4298         if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_TWO], duration)) {
4299             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4300                 NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "duration", "number"));
4301             return result;
4302         }
4303     }
4304 
4305     WebviewController *webviewController = nullptr;
4306     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
4307     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
4308         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4309         return nullptr;
4310     }
4311     if (argc == INTEGER_THREE) {
4312         webviewController->ScrollToWithAnime(x, y, duration);
4313     } else {
4314         webviewController->ScrollTo(x, y);
4315     }
4316     return result;
4317 }
4318 
ScrollBy(napi_env env, napi_callback_info info)4319 napi_value NapiWebviewController::ScrollBy(napi_env env, napi_callback_info info)
4320 {
4321     napi_value thisVar = nullptr;
4322     napi_value result = nullptr;
4323     size_t argc = INTEGER_THREE;
4324     napi_value argv[INTEGER_THREE] = { 0 };
4325     float deltaX;
4326     float deltaY;
4327     int32_t duration = 0;
4328 
4329     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4330     if (argc != INTEGER_TWO && argc != INTEGER_THREE) {
4331         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4332             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_TWO, "two", "three"));
4333         return result;
4334     }
4335 
4336     if (!NapiParseUtils::ParseFloat(env, argv[INTEGER_ZERO], deltaX)) {
4337         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4338             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "deltaX", "number"));
4339         return result;
4340     }
4341 
4342     if (!NapiParseUtils::ParseFloat(env, argv[INTEGER_ONE], deltaY)) {
4343         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4344             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "deltaY", "number"));
4345         return result;
4346     }
4347 
4348     if (argc == INTEGER_THREE) {
4349         if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_TWO], duration)) {
4350             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4351                 NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "duration", "number"));
4352             return result;
4353         }
4354     }
4355 
4356     WebviewController *webviewController = nullptr;
4357     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
4358     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
4359         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4360         return nullptr;
4361     }
4362     if (argc == INTEGER_THREE) {
4363         webviewController->ScrollByWithAnime(deltaX, deltaY, duration);
4364     } else {
4365         webviewController->ScrollBy(deltaX, deltaY);
4366     }
4367     return result;
4368 }
4369 
SlideScroll(napi_env env, napi_callback_info info)4370 napi_value NapiWebviewController::SlideScroll(napi_env env, napi_callback_info info)
4371 {
4372     napi_value thisVar = nullptr;
4373     napi_value result = nullptr;
4374     size_t argc = INTEGER_TWO;
4375     napi_value argv[INTEGER_TWO] = { 0 };
4376     float vx;
4377     float vy;
4378 
4379     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4380     if (argc != INTEGER_TWO) {
4381         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4382             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "two"));
4383         return result;
4384     }
4385 
4386     if (!NapiParseUtils::ParseFloat(env, argv[INTEGER_ZERO], vx)) {
4387         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4388             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "vx", "number"));
4389         return result;
4390     }
4391 
4392     if (!NapiParseUtils::ParseFloat(env, argv[INTEGER_ONE], vy)) {
4393         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4394             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "vy", "number"));
4395         return result;
4396     }
4397 
4398     WebviewController *webviewController = nullptr;
4399     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
4400     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
4401         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4402         return nullptr;
4403     }
4404     webviewController->SlideScroll(vx, vy);
4405     return result;
4406 }
4407 
SetScrollable(napi_env env, napi_callback_info info)4408 napi_value NapiWebviewController::SetScrollable(napi_env env, napi_callback_info info)
4409 {
4410     napi_value thisVar = nullptr;
4411     napi_value result = nullptr;
4412     size_t argc = INTEGER_TWO;
4413     size_t argcForOld = INTEGER_ONE;
4414     napi_value argv[INTEGER_TWO] = { 0 };
4415 
4416     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4417     if (argc != INTEGER_TWO && argc != argcForOld) {
4418         NWebError::BusinessError::ThrowErrorByErrcode(env, NWebError::PARAM_CHECK_ERROR,
4419             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_TWO, "one", "two"));
4420         return result;
4421     }
4422     bool isEnableScroll;
4423     if (!NapiParseUtils::ParseBoolean(env, argv[0], isEnableScroll)) {
4424         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4425             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "enable", "boolean"));
4426         return result;
4427     }
4428 
4429     int32_t scrollType = -1;
4430     if (argc == INTEGER_TWO) {
4431         if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_ONE], scrollType) || scrollType < 0 ||
4432             scrollType >= INTEGER_ONE) {
4433             WVLOG_E("BusinessError: 401. The character of 'scrollType' must be int32.");
4434             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4435             return result;
4436         }
4437     }
4438 
4439     WebviewController* webviewController = nullptr;
4440     napi_status status = napi_unwrap(env, thisVar, (void**)&webviewController);
4441     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
4442         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4443         return nullptr;
4444     }
4445     webviewController->SetScrollable(isEnableScroll, scrollType);
4446     return result;
4447 }
4448 
GetScrollable(napi_env env, napi_callback_info info)4449 napi_value NapiWebviewController::GetScrollable(napi_env env, napi_callback_info info)
4450 {
4451     napi_value result = nullptr;
4452     WebviewController *webviewController = GetWebviewController(env, info);
4453     if (!webviewController) {
4454         return nullptr;
4455     }
4456 
4457     bool isScrollable = webviewController->GetScrollable();
4458     NAPI_CALL(env, napi_get_boolean(env, isScrollable, &result));
4459     return result;
4460 }
4461 
InnerGetCertificate(napi_env env, napi_callback_info info)4462 napi_value NapiWebviewController::InnerGetCertificate(napi_env env, napi_callback_info info)
4463 {
4464     napi_value thisVar = nullptr;
4465     napi_value result = nullptr;
4466     napi_get_cb_info(env, info, nullptr, nullptr, &thisVar, nullptr);
4467     napi_create_array(env, &result);
4468 
4469     WebviewController *webviewController = nullptr;
4470     napi_unwrap(env, thisVar, (void **)&webviewController);
4471     if (!webviewController || !webviewController->IsInit()) {
4472         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4473         return result;
4474     }
4475 
4476     std::vector<std::string> certChainDerData;
4477     bool ans = webviewController->GetCertChainDerData(certChainDerData);
4478     if (!ans) {
4479         WVLOG_E("get cert chain data failed");
4480         return result;
4481     }
4482 
4483     for (uint8_t i = 0; i < certChainDerData.size(); i++) {
4484         if (i == UINT8_MAX) {
4485             WVLOG_E("error, cert chain data array reach max");
4486             break;
4487         }
4488         void *data = nullptr;
4489         napi_value buffer = nullptr;
4490         napi_value item = nullptr;
4491         NAPI_CALL(env, napi_create_arraybuffer(env, certChainDerData[i].size(), &data, &buffer));
4492         int retCode = memcpy_s(data, certChainDerData[i].size(),
4493                                certChainDerData[i].data(), certChainDerData[i].size());
4494         if (retCode != 0) {
4495             WVLOG_E("memcpy_s cert data failed, index = %{public}u,", i);
4496             continue;
4497         }
4498         NAPI_CALL(env, napi_create_typedarray(env, napi_uint8_array, certChainDerData[i].size(), buffer, 0, &item));
4499         NAPI_CALL(env, napi_set_element(env, result, i, item));
4500     }
4501     return result;
4502 }
4503 
SetAudioMuted(napi_env env, napi_callback_info info)4504 napi_value NapiWebviewController::SetAudioMuted(napi_env env, napi_callback_info info)
4505 {
4506     WVLOG_D("SetAudioMuted invoked");
4507 
4508     napi_value result = nullptr;
4509     NAPI_CALL(env, napi_get_undefined(env, &result));
4510 
4511     napi_value thisVar = nullptr;
4512     size_t argc = INTEGER_ONE;
4513     napi_value argv[INTEGER_ONE] = { 0 };
4514     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4515     if (argc != INTEGER_ONE) {
4516         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4517             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
4518         return result;
4519     }
4520 
4521     bool muted = false;
4522     if (!NapiParseUtils::ParseBoolean(env, argv[0], muted)) {
4523         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4524             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "mute", "boolean"));
4525         return result;
4526     }
4527 
4528     WebviewController* webviewController = nullptr;
4529     napi_status status = napi_unwrap(env, thisVar, (void**)&webviewController);
4530     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
4531         WVLOG_E("SetAudioMuted failed due to no associated Web component");
4532         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4533         return result;
4534     }
4535 
4536     ErrCode ret = webviewController->SetAudioMuted(muted);
4537     if (ret != NO_ERROR) {
4538         WVLOG_E("SetAudioMuted failed, error code: %{public}d", ret);
4539         BusinessError::ThrowErrorByErrcode(env, ret);
4540         return result;
4541     }
4542 
4543     WVLOG_I("SetAudioMuted: %{public}s", (muted ? "true" : "false"));
4544     return result;
4545 }
4546 
PrefetchPage(napi_env env, napi_callback_info info)4547 napi_value NapiWebviewController::PrefetchPage(napi_env env, napi_callback_info info)
4548 {
4549     napi_value thisVar = nullptr;
4550     napi_value result = nullptr;
4551     size_t argc = INTEGER_TWO;
4552     napi_value argv[INTEGER_TWO];
4553     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4554     WebviewController *webviewController = nullptr;
4555     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
4556     if ((argc != INTEGER_ONE) && (argc != INTEGER_TWO)) {
4557         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4558         return nullptr;
4559     }
4560     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
4561         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4562         return nullptr;
4563     }
4564     std::string url;
4565     if (!ParsePrepareUrl(env, argv[INTEGER_ZERO], url)) {
4566         BusinessError::ThrowErrorByErrcode(env, INVALID_URL);
4567         return nullptr;
4568     }
4569     std::map<std::string, std::string> additionalHttpHeaders;
4570     if (argc == INTEGER_ONE) {
4571         ErrCode ret = webviewController->PrefetchPage(url, additionalHttpHeaders);
4572         if (ret != NO_ERROR) {
4573             WVLOG_E("PrefetchPage failed, error code: %{public}d", ret);
4574             BusinessError::ThrowErrorByErrcode(env, ret);
4575             return nullptr;
4576         }
4577         NAPI_CALL(env, napi_get_undefined(env, &result));
4578         return result;
4579     }
4580     return PrefetchPageWithHttpHeaders(env, info, url, argv, webviewController);
4581 }
4582 
PrefetchPageWithHttpHeaders(napi_env env, napi_callback_info info, std::string& url, const napi_value* argv, WebviewController* webviewController)4583 napi_value NapiWebviewController::PrefetchPageWithHttpHeaders(napi_env env, napi_callback_info info, std::string& url,
4584     const napi_value* argv, WebviewController* webviewController)
4585 {
4586     napi_value result = nullptr;
4587     std::map<std::string, std::string> additionalHttpHeaders;
4588     napi_value array = argv[INTEGER_ONE];
4589     bool isArray = false;
4590     napi_is_array(env, array, &isArray);
4591     if (isArray) {
4592         uint32_t arrayLength = INTEGER_ZERO;
4593         napi_get_array_length(env, array, &arrayLength);
4594         for (uint32_t i = 0; i < arrayLength; ++i) {
4595             std::string key;
4596             std::string value;
4597             napi_value obj = nullptr;
4598             napi_value keyObj = nullptr;
4599             napi_value valueObj = nullptr;
4600             napi_get_element(env, array, i, &obj);
4601             if (napi_get_named_property(env, obj, "headerKey", &keyObj) != napi_ok) {
4602                 continue;
4603             }
4604             if (napi_get_named_property(env, obj, "headerValue", &valueObj) != napi_ok) {
4605                 continue;
4606             }
4607             NapiParseUtils::ParseString(env, keyObj, key);
4608             NapiParseUtils::ParseString(env, valueObj, value);
4609             additionalHttpHeaders[key] = value;
4610         }
4611     } else {
4612         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4613         return nullptr;
4614     }
4615 
4616     ErrCode ret = webviewController->PrefetchPage(url, additionalHttpHeaders);
4617     if (ret != NO_ERROR) {
4618         WVLOG_E("PrefetchPage failed, error code: %{public}d", ret);
4619         BusinessError::ThrowErrorByErrcode(env, ret);
4620         return nullptr;
4621     }
4622     NAPI_CALL(env, napi_get_undefined(env, &result));
4623     return result;
4624 }
4625 
GetLastJavascriptProxyCallingFrameUrl(napi_env env, napi_callback_info info)4626 napi_value NapiWebviewController::GetLastJavascriptProxyCallingFrameUrl(napi_env env, napi_callback_info info)
4627 {
4628     napi_value result = nullptr;
4629     WebviewController *webviewController = GetWebviewController(env, info);
4630     if (!webviewController) {
4631         return nullptr;
4632     }
4633 
4634     std::string lastCallingFrameUrl = webviewController->GetLastJavascriptProxyCallingFrameUrl();
4635     napi_create_string_utf8(env, lastCallingFrameUrl.c_str(), lastCallingFrameUrl.length(), &result);
4636     return result;
4637 }
4638 
PrepareForPageLoad(napi_env env, napi_callback_info info)4639 napi_value NapiWebviewController::PrepareForPageLoad(napi_env env, napi_callback_info info)
4640 {
4641     napi_value thisVar = nullptr;
4642     napi_value result = nullptr;
4643     size_t argc = INTEGER_THREE;
4644     napi_value argv[INTEGER_THREE] = { 0 };
4645     napi_get_undefined(env, &result);
4646     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4647     if (argc != INTEGER_THREE) {
4648         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4649         return nullptr;
4650     }
4651 
4652     std::string url;
4653     if (!ParsePrepareUrl(env, argv[INTEGER_ZERO], url)) {
4654         BusinessError::ThrowErrorByErrcode(env, INVALID_URL);
4655         return nullptr;
4656     }
4657 
4658     bool preconnectable = false;
4659     if (!NapiParseUtils::ParseBoolean(env, argv[INTEGER_ONE], preconnectable)) {
4660         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4661         return nullptr;
4662     }
4663 
4664     int32_t numSockets = 0;
4665     if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_TWO], numSockets)) {
4666         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4667         return nullptr;
4668     }
4669     if (numSockets <= 0 || static_cast<uint32_t>(numSockets) > SOCKET_MAXIMUM) {
4670         BusinessError::ThrowErrorByErrcode(env, INVALID_SOCKET_NUMBER);
4671         return nullptr;
4672     }
4673 
4674     NWebHelper::Instance().PrepareForPageLoad(url, preconnectable, numSockets);
4675     NAPI_CALL(env, napi_get_undefined(env, &result));
4676     return result;
4677 }
4678 
PrefetchResource(napi_env env, napi_callback_info info)4679 napi_value NapiWebviewController::PrefetchResource(napi_env env, napi_callback_info info)
4680 {
4681     napi_value thisVar = nullptr;
4682     napi_value result = nullptr;
4683     size_t argc = INTEGER_FOUR;
4684     napi_value argv[INTEGER_FOUR] = { 0 };
4685     napi_get_undefined(env, &result);
4686     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4687     if (argc > INTEGER_FOUR || argc < INTEGER_ONE) {
4688         WVLOG_E("BusinessError: 401. Arg count must between 1 and 4.");
4689         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4690         return nullptr;
4691     }
4692 
4693     std::shared_ptr<NWebEnginePrefetchArgs> prefetchArgs = ParsePrefetchArgs(env, argv[INTEGER_ZERO]);
4694     if (prefetchArgs == nullptr) {
4695         return nullptr;
4696     }
4697 
4698     std::map<std::string, std::string> additionalHttpHeaders;
4699     if (argc >= INTEGER_TWO && !ParseHttpHeaders(env, argv[INTEGER_ONE], &additionalHttpHeaders)) {
4700         WVLOG_E("BusinessError: 401. The type of 'additionalHttpHeaders' must be Array of 'WebHeader'.");
4701         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4702         return nullptr;
4703     }
4704 
4705     std::string cacheKey;
4706     if ((argc >= INTEGER_THREE) && !NapiParseUtils::ParseString(env, argv[INTEGER_TWO], cacheKey)) {
4707         WVLOG_E("BusinessError: 401.The type of 'cacheKey' must be string.");
4708         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4709         return nullptr;
4710     }
4711 
4712     if (cacheKey.empty()) {
4713         cacheKey = prefetchArgs->GetUrl();
4714     } else {
4715         if (!CheckCacheKey(env, cacheKey)) {
4716             return nullptr;
4717         }
4718     }
4719 
4720     int32_t cacheValidTime = 0;
4721     if (argc >= INTEGER_FOUR) {
4722         if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_THREE], cacheValidTime) || cacheValidTime <= 0 ||
4723             cacheValidTime > INT_MAX) {
4724             WVLOG_E("BusinessError: 401. The character of 'cacheValidTime' must be int32.");
4725             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4726             return nullptr;
4727         }
4728     }
4729 
4730     NAPI_CALL(env, napi_get_undefined(env, &result));
4731     NWebHelper::Instance().PrefetchResource(prefetchArgs, additionalHttpHeaders, cacheKey, cacheValidTime);
4732     return result;
4733 }
4734 
ClearPrefetchedResource(napi_env env, napi_callback_info info)4735 napi_value NapiWebviewController::ClearPrefetchedResource(napi_env env, napi_callback_info info)
4736 {
4737     napi_value thisVar = nullptr;
4738     napi_value result = nullptr;
4739     size_t argc = INTEGER_ONE;
4740     napi_value argv[INTEGER_ONE] = { 0 };
4741     napi_get_undefined(env, &result);
4742     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4743     if (argc != INTEGER_ONE) {
4744         WVLOG_E("BusinessError: 401. Arg count must be 1.");
4745         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4746         return nullptr;
4747     }
4748 
4749     std::vector<std::string> cacheKeyList;
4750     if (!ParseCacheKeyList(env, argv[INTEGER_ZERO], &cacheKeyList)) {
4751         WVLOG_E("BusinessError: 401. The type of 'cacheKeyList' must be Array of string.");
4752         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4753         return nullptr;
4754     }
4755 
4756     NAPI_CALL(env, napi_get_undefined(env, &result));
4757     NWebHelper::Instance().ClearPrefetchedResource(cacheKeyList);
4758     return result;
4759 }
4760 
SetDownloadDelegate(napi_env env, napi_callback_info info)4761 napi_value NapiWebviewController::SetDownloadDelegate(napi_env env, napi_callback_info info)
4762 {
4763     WVLOG_D("WebDownloader::JS_SetDownloadDelegate");
4764     NWebHelper::Instance().LoadNWebSDK();
4765     size_t argc = 1;
4766     napi_value argv[1] = {0};
4767     napi_value thisVar = nullptr;
4768     void* data = nullptr;
4769     napi_get_cb_info(env, info, &argc, argv, &thisVar, &data);
4770 
4771     WebDownloadDelegate* delegate = nullptr;
4772     napi_value obj = argv[0];
4773     napi_unwrap(env, obj, (void**)&delegate);
4774     if (!delegate) {
4775         WVLOG_E("[DOWNLOAD] WebDownloader::JS_SetDownloadDelegate delegate is null");
4776         (void)RemoveDownloadDelegateRef(env, thisVar);
4777         return nullptr;
4778     }
4779     napi_create_reference(env, obj, 1, &delegate->delegate_);
4780 
4781     WebviewController *webviewController = nullptr;
4782     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webviewController));
4783     if (webviewController == nullptr || !webviewController->IsInit()) {
4784         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4785         WVLOG_E("create message port failed, napi unwrap webviewController failed");
4786         return nullptr;
4787     }
4788     int32_t nwebId = webviewController->GetWebId();
4789     WebDownloadManager::AddDownloadDelegateForWeb(nwebId, delegate);
4790     return nullptr;
4791 }
4792 
StartDownload(napi_env env, napi_callback_info info)4793 napi_value NapiWebviewController::StartDownload(napi_env env, napi_callback_info info)
4794 {
4795     WVLOG_D("[DOWNLOAD] NapiWebviewController::StartDownload");
4796     size_t argc = 1;
4797     napi_value argv[1] = {0};
4798     napi_value thisVar = nullptr;
4799     void* data = nullptr;
4800     napi_get_cb_info(env, info, &argc, argv, &thisVar, &data);
4801 
4802     WebviewController *webviewController = nullptr;
4803     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webviewController));
4804     if (webviewController == nullptr || !webviewController->IsInit()) {
4805         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4806         WVLOG_E("create message port failed, napi unwrap webviewController failed");
4807         return nullptr;
4808     }
4809 
4810     std::string url;
4811     if (!ParsePrepareUrl(env, argv[INTEGER_ZERO], url)) {
4812         BusinessError::ThrowErrorByErrcode(env, INVALID_URL);
4813         return nullptr;
4814     }
4815     int32_t nwebId = webviewController->GetWebId();
4816     NWebHelper::Instance().LoadNWebSDK();
4817     WebDownloader_StartDownload(nwebId, url.c_str());
4818     return nullptr;
4819 }
4820 
CloseAllMediaPresentations(napi_env env, napi_callback_info info)4821 napi_value NapiWebviewController::CloseAllMediaPresentations(napi_env env, napi_callback_info info)
4822 {
4823     napi_value result = nullptr;
4824     WebviewController* webviewController = GetWebviewController(env, info);
4825     if (!webviewController) {
4826         return result;
4827     }
4828 
4829     webviewController->CloseAllMediaPresentations();
4830     NAPI_CALL(env, napi_get_undefined(env, &result));
4831     return result;
4832 }
4833 
StopAllMedia(napi_env env, napi_callback_info info)4834 napi_value NapiWebviewController::StopAllMedia(napi_env env, napi_callback_info info)
4835 {
4836     napi_value result = nullptr;
4837     WebviewController* webviewController = GetWebviewController(env, info);
4838     if (!webviewController) {
4839         return result;
4840     }
4841 
4842     webviewController->StopAllMedia();
4843     NAPI_CALL(env, napi_get_undefined(env, &result));
4844     return result;
4845 }
4846 
ResumeAllMedia(napi_env env, napi_callback_info info)4847 napi_value NapiWebviewController::ResumeAllMedia(napi_env env, napi_callback_info info)
4848 {
4849     napi_value result = nullptr;
4850     WebviewController* webviewController = GetWebviewController(env, info);
4851     if (!webviewController) {
4852         return result;
4853     }
4854 
4855     webviewController->ResumeAllMedia();
4856     NAPI_CALL(env, napi_get_undefined(env, &result));
4857     return result;
4858 }
4859 
PauseAllMedia(napi_env env, napi_callback_info info)4860 napi_value NapiWebviewController::PauseAllMedia(napi_env env, napi_callback_info info)
4861 {
4862     napi_value result = nullptr;
4863     WebviewController* webviewController = GetWebviewController(env, info);
4864     if (!webviewController) {
4865         return result;
4866     }
4867 
4868     webviewController->PauseAllMedia();
4869     NAPI_CALL(env, napi_get_undefined(env, &result));
4870     return result;
4871 }
4872 
GetMediaPlaybackState(napi_env env, napi_callback_info info)4873 napi_value NapiWebviewController::GetMediaPlaybackState(napi_env env, napi_callback_info info)
4874 {
4875     napi_value result = nullptr;
4876     WebviewController* webviewController = GetWebviewController(env, info);
4877     if (!webviewController) {
4878         return result;
4879     }
4880 
4881     int32_t mediaPlaybackState = webviewController->GetMediaPlaybackState();
4882     napi_create_int32(env, mediaPlaybackState, &result);
4883     return result;
4884 }
4885 
SetConnectionTimeout(napi_env env, napi_callback_info info)4886 napi_value NapiWebviewController::SetConnectionTimeout(napi_env env, napi_callback_info info)
4887 {
4888     napi_value result = nullptr;
4889     size_t argc = INTEGER_ONE;
4890     napi_value argv[INTEGER_ONE] = { nullptr };
4891     napi_get_cb_info(env, info, &argc, argv, nullptr, nullptr);
4892     if (argc != INTEGER_ONE) {
4893         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4894                 NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
4895         return result;
4896     }
4897 
4898     int32_t timeout = 0;
4899     if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_ZERO], timeout) || (timeout <= 0)) {
4900         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4901                 "BusinessError: 401. Parameter error. The type of 'timeout' must be int and must be positive integer.");
4902         return result;
4903     }
4904 
4905     NWebHelper::Instance().SetConnectionTimeout(timeout);
4906     NAPI_CALL(env, napi_get_undefined(env, &result));
4907     return result;
4908 }
4909 
CreateWebPrintDocumentAdapter(napi_env env, napi_callback_info info)4910 napi_value NapiWebviewController::CreateWebPrintDocumentAdapter(napi_env env, napi_callback_info info)
4911 {
4912     WVLOG_I("Create web print document adapter.");
4913     napi_value thisVar = nullptr;
4914     napi_value result = nullptr;
4915     size_t argc = INTEGER_ONE;
4916     napi_value argv[INTEGER_ONE];
4917     NAPI_CALL(env, napi_get_undefined(env, &result));
4918     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
4919     if (argc != INTEGER_ONE) {
4920         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4921             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
4922         return result;
4923     }
4924     std::string jobName;
4925     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], jobName)) {
4926         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
4927             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "jopName", "string"));
4928         return result;
4929     }
4930     WebviewController *webviewController = nullptr;
4931     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
4932     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
4933         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
4934         return result;
4935     }
4936     void* webPrintDocument = webviewController->CreateWebPrintDocumentAdapter(jobName);
4937     if (!webPrintDocument) {
4938         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4939         return result;
4940     }
4941     napi_handle_scope scope = nullptr;
4942     napi_open_handle_scope(env, &scope);
4943     if (scope == nullptr) {
4944         return result;
4945     }
4946     napi_value webPrintDoc = nullptr;
4947     NAPI_CALL(env, napi_get_reference_value(env, g_webPrintDocClassRef, &webPrintDoc));
4948     napi_value consParam[INTEGER_ONE] = {0};
4949     NAPI_CALL(env, napi_create_bigint_uint64(env, reinterpret_cast<uint64_t>(webPrintDocument),
4950                                              &consParam[INTEGER_ZERO]));
4951     napi_value proxy = nullptr;
4952     status = napi_new_instance(env, webPrintDoc, INTEGER_ONE, &consParam[INTEGER_ZERO], &proxy);
4953     if (status!= napi_ok) {
4954         napi_close_handle_scope(env, scope);
4955         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
4956         return result;
4957     }
4958     napi_close_handle_scope(env, scope);
4959     return proxy;
4960 }
4961 
GetSecurityLevel(napi_env env, napi_callback_info info)4962 napi_value NapiWebviewController::GetSecurityLevel(napi_env env, napi_callback_info info)
4963 {
4964     napi_value result = nullptr;
4965     WebviewController *webviewController = GetWebviewController(env, info);
4966     if (!webviewController) {
4967         return result;
4968     }
4969 
4970     int32_t securityLevel = webviewController->GetSecurityLevel();
4971     napi_create_int32(env, securityLevel, &result);
4972     return result;
4973 }
4974 
ParsePrintRangeAdapter(napi_env env, napi_value pageRange, PrintAttributesAdapter& printAttr)4975 void ParsePrintRangeAdapter(napi_env env, napi_value pageRange, PrintAttributesAdapter& printAttr)
4976 {
4977     if (!pageRange) {
4978         WVLOG_E("ParsePrintRangeAdapter failed.");
4979         return;
4980     }
4981     napi_value startPage = nullptr;
4982     napi_value endPage = nullptr;
4983     napi_value pages = nullptr;
4984     napi_get_named_property(env, pageRange, "startPage", &startPage);
4985     napi_get_named_property(env, pageRange, "endPage", &endPage);
4986     if (startPage) {
4987         NapiParseUtils::ParseUint32(env, startPage, printAttr.pageRange.startPage);
4988     }
4989     if (endPage) {
4990         NapiParseUtils::ParseUint32(env, endPage, printAttr.pageRange.endPage);
4991     }
4992     napi_get_named_property(env, pageRange, "pages", &pages);
4993     uint32_t pageArrayLength = 0;
4994     napi_get_array_length(env, pages, &pageArrayLength);
4995     for (uint32_t i = 0; i < pageArrayLength; ++i) {
4996         napi_value pagesNumObj = nullptr;
4997         napi_get_element(env, pages, i, &pagesNumObj);
4998         uint32_t pagesNum;
4999         NapiParseUtils::ParseUint32(env, pagesNumObj, pagesNum);
5000         printAttr.pageRange.pages.push_back(pagesNum);
5001     }
5002 }
5003 
ParsePrintPageSizeAdapter(napi_env env, napi_value pageSize, PrintAttributesAdapter& printAttr)5004 void ParsePrintPageSizeAdapter(napi_env env, napi_value pageSize, PrintAttributesAdapter& printAttr)
5005 {
5006     if (!pageSize) {
5007         WVLOG_E("ParsePrintPageSizeAdapter failed.");
5008         return;
5009     }
5010     napi_value id = nullptr;
5011     napi_value name = nullptr;
5012     napi_value width = nullptr;
5013     napi_value height = nullptr;
5014     napi_get_named_property(env, pageSize, "id", &id);
5015     napi_get_named_property(env, pageSize, "name", &name);
5016     napi_get_named_property(env, pageSize, "width", &width);
5017     napi_get_named_property(env, pageSize, "height", &height);
5018     if (width) {
5019         NapiParseUtils::ParseUint32(env, width, printAttr.pageSize.width);
5020     }
5021     if (height) {
5022         NapiParseUtils::ParseUint32(env, height, printAttr.pageSize.height);
5023     }
5024 }
5025 
ParsePrintMarginAdapter(napi_env env, napi_value margin, PrintAttributesAdapter& printAttr)5026 void ParsePrintMarginAdapter(napi_env env, napi_value margin, PrintAttributesAdapter& printAttr)
5027 {
5028     if (!margin) {
5029         WVLOG_E("ParsePrintMarginAdapter failed.");
5030         return;
5031     }
5032     napi_value top = nullptr;
5033     napi_value bottom = nullptr;
5034     napi_value left = nullptr;
5035     napi_value right = nullptr;
5036     napi_get_named_property(env, margin, "top", &top);
5037     napi_get_named_property(env, margin, "bottom", &bottom);
5038     napi_get_named_property(env, margin, "left", &left);
5039     napi_get_named_property(env, margin, "right", &right);
5040     if (top) {
5041         NapiParseUtils::ParseUint32(env, top, printAttr.margin.top);
5042     }
5043     if (bottom) {
5044         NapiParseUtils::ParseUint32(env, bottom, printAttr.margin.bottom);
5045     }
5046     if (left) {
5047         NapiParseUtils::ParseUint32(env, left, printAttr.margin.left);
5048     }
5049     if (right) {
5050         NapiParseUtils::ParseUint32(env, right, printAttr.margin.right);
5051     }
5052 }
5053 
ParseWebPrintWriteResultCallback(napi_env env, napi_value argv)5054 WebPrintWriteResultCallback ParseWebPrintWriteResultCallback(napi_env env, napi_value argv)
5055 {
5056     if (!argv) {
5057         WVLOG_E("ParseWebPrintWriteResultCallback failed.");
5058         return nullptr;
5059     }
5060     napi_ref jsCallback = nullptr;
5061     napi_create_reference(env, argv, 1, &jsCallback);
5062     if (jsCallback) {
5063         WebPrintWriteResultCallback callbackImpl =
5064             [env, jCallback = std::move(jsCallback)](std::string jobId, uint32_t state) {
5065             if (!env) {
5066                 return;
5067             }
5068             napi_handle_scope scope = nullptr;
5069             napi_open_handle_scope(env, &scope);
5070             if (scope == nullptr) {
5071                 return;
5072             }
5073             napi_value setResult[INTEGER_TWO] = {0};
5074             napi_create_string_utf8(env, jobId.c_str(), NAPI_AUTO_LENGTH, &setResult[INTEGER_ZERO]);
5075             napi_create_uint32(env, state, &setResult[INTEGER_ONE]);
5076             napi_value args[INTEGER_TWO] = {setResult[INTEGER_ZERO], setResult[INTEGER_ONE]};
5077             napi_value callback = nullptr;
5078             napi_get_reference_value(env, jCallback, &callback);
5079             napi_value callbackResult = nullptr;
5080             napi_call_function(env, nullptr, callback, INTEGER_TWO, args, &callbackResult);
5081             napi_delete_reference(env, jCallback);
5082             napi_close_handle_scope(env, scope);
5083         };
5084         return callbackImpl;
5085     }
5086     return nullptr;
5087 }
5088 
ParseWebPrintAttrParams(napi_env env, napi_value obj, PrintAttributesAdapter& printAttr)5089 bool ParseWebPrintAttrParams(napi_env env, napi_value obj, PrintAttributesAdapter& printAttr)
5090 {
5091     if (!obj) {
5092         WVLOG_E("ParseWebPrintAttrParams failed.");
5093         return false;
5094     }
5095     napi_value copyNumber = nullptr;
5096     napi_value pageRange = nullptr;
5097     napi_value isSequential = nullptr;
5098     napi_value pageSize = nullptr;
5099     napi_value isLandscape = nullptr;
5100     napi_value colorMode = nullptr;
5101     napi_value duplexMode = nullptr;
5102     napi_value margin = nullptr;
5103     napi_value option = nullptr;
5104     napi_get_named_property(env, obj, "copyNumber", &copyNumber);
5105     napi_get_named_property(env, obj, "pageRange", &pageRange);
5106     napi_get_named_property(env, obj, "isSequential", &isSequential);
5107     napi_get_named_property(env, obj, "pageSize", &pageSize);
5108     napi_get_named_property(env, obj, "isLandscape", &isLandscape);
5109     napi_get_named_property(env, obj, "colorMode", &colorMode);
5110     napi_get_named_property(env, obj, "duplexMode", &duplexMode);
5111     napi_get_named_property(env, obj, "margin", &margin);
5112     napi_get_named_property(env, obj, "option", &option);
5113     if (copyNumber) {
5114         NapiParseUtils::ParseUint32(env, copyNumber, printAttr.copyNumber);
5115     }
5116     if (isSequential) {
5117         NapiParseUtils::ParseBoolean(env, isSequential, printAttr.isSequential);
5118     }
5119     if (isLandscape) {
5120         NapiParseUtils::ParseBoolean(env, isLandscape,  printAttr.isLandscape);
5121     }
5122     if (colorMode) {
5123         NapiParseUtils::ParseUint32(env, colorMode, printAttr.colorMode);
5124     }
5125     if (duplexMode) {
5126         NapiParseUtils::ParseUint32(env, duplexMode, printAttr.duplexMode);
5127     }
5128     if (option) {
5129         NapiParseUtils::ParseString(env, option, printAttr.option);
5130     }
5131     ParsePrintRangeAdapter(env, pageRange, printAttr);
5132     ParsePrintPageSizeAdapter(env, pageSize, printAttr);
5133     ParsePrintMarginAdapter(env, margin, printAttr);
5134     return true;
5135 }
5136 
OnStartLayoutWrite(napi_env env, napi_callback_info info)5137 napi_value NapiWebPrintDocument::OnStartLayoutWrite(napi_env env, napi_callback_info info)
5138 {
5139     WVLOG_I("On Start Layout Write.");
5140     napi_value thisVar = nullptr;
5141     napi_value result = nullptr;
5142     size_t argc = INTEGER_FIVE;
5143     napi_value argv[INTEGER_FIVE] = { 0 };
5144     WebPrintDocument *webPrintDocument = nullptr;
5145 
5146     NAPI_CALL(env, napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
5147     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webPrintDocument));
5148     if (webPrintDocument == nullptr) {
5149         WVLOG_E("unwrap webPrintDocument failed.");
5150         return result;
5151     }
5152 
5153     std::string jobId;
5154     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], jobId)) {
5155         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5156         return result;
5157     }
5158 
5159     int32_t fd;
5160     if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_THREE], fd)) {
5161         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5162         return result;
5163     }
5164     PrintAttributesAdapter oldPrintAttr;
5165     PrintAttributesAdapter newPrintAttr;
5166     bool ret = false;
5167     ret = ParseWebPrintAttrParams(env, argv[INTEGER_ONE], oldPrintAttr);
5168     if (!ret) {
5169         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5170         return result;
5171     }
5172     ret = ParseWebPrintAttrParams(env, argv[INTEGER_TWO], newPrintAttr);
5173     if (!ret) {
5174         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5175         return result;
5176     }
5177     WebPrintWriteResultCallback writeResultCallback = nullptr;
5178     writeResultCallback = ParseWebPrintWriteResultCallback(env, argv[INTEGER_FOUR]);
5179     webPrintDocument->OnStartLayoutWrite(jobId, oldPrintAttr, newPrintAttr, fd, writeResultCallback);
5180     return result;
5181 }
5182 
OnJobStateChanged(napi_env env, napi_callback_info info)5183 napi_value NapiWebPrintDocument::OnJobStateChanged(napi_env env, napi_callback_info info)
5184 {
5185     WVLOG_I("On Job State Changed.");
5186     napi_value thisVar = nullptr;
5187     napi_value result = nullptr;
5188     size_t argc = INTEGER_TWO;
5189     napi_value argv[INTEGER_TWO];
5190     NAPI_CALL(env, napi_get_undefined(env, &result));
5191 
5192     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5193     WebPrintDocument *webPrintDocument = nullptr;
5194     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webPrintDocument));
5195     if (webPrintDocument == nullptr) {
5196         WVLOG_E("unwrap webPrintDocument failed.");
5197         return result;
5198     }
5199     if (argc != INTEGER_TWO) {
5200         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5201         return result;
5202     }
5203 
5204     std::string jobId;
5205     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], jobId)) {
5206         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5207         return result;
5208     }
5209 
5210     int32_t state;
5211     if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_ONE], state)) {
5212         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5213         return result;
5214     }
5215     webPrintDocument->OnJobStateChanged(jobId, state);
5216     return result;
5217 }
5218 
JsConstructor(napi_env env, napi_callback_info info)5219 napi_value NapiWebPrintDocument::JsConstructor(napi_env env, napi_callback_info info)
5220 {
5221     napi_value thisVar = nullptr;
5222     size_t argc = INTEGER_ONE;
5223     napi_value argv[INTEGER_ONE];
5224     uint64_t addrWebPrintDoc = 0;
5225     bool loseLess = true;
5226     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5227 
5228     if (!NapiParseUtils::ParseUint64(env, argv[INTEGER_ZERO], addrWebPrintDoc, &loseLess)) {
5229         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5230         return nullptr;
5231     }
5232     void *webPrintDocPtr = reinterpret_cast<void *>(addrWebPrintDoc);
5233     WebPrintDocument *webPrintDoc = new (std::nothrow) WebPrintDocument(webPrintDocPtr);
5234     if (webPrintDoc == nullptr) {
5235         WVLOG_E("new web print failed");
5236         return nullptr;
5237     }
5238     NAPI_CALL(env, napi_wrap(env, thisVar, webPrintDoc,
5239         [](napi_env env, void *data, void *hint) {
5240             WebPrintDocument *webPrintDocument = static_cast<WebPrintDocument *>(data);
5241             delete webPrintDocument;
5242         },
5243         nullptr, nullptr));
5244     return thisVar;
5245 }
5246 
SetPrintBackground(napi_env env, napi_callback_info info)5247 napi_value NapiWebviewController::SetPrintBackground(napi_env env, napi_callback_info info)
5248 {
5249     napi_value result = nullptr;
5250     napi_value thisVar = nullptr;
5251     size_t argc = INTEGER_ONE;
5252     napi_value argv[INTEGER_ONE] = { 0 };
5253 
5254     NAPI_CALL(env, napi_get_undefined(env, &result));
5255     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5256     if (argc != INTEGER_ONE) {
5257         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5258             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
5259         return result;
5260     }
5261 
5262     bool printBackgroundEnabled = false;
5263     if (!NapiParseUtils::ParseBoolean(env, argv[0], printBackgroundEnabled)) {
5264         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5265             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "enable", "boolean"));
5266         return result;
5267     }
5268 
5269     WebviewController *webviewController = GetWebviewController(env, info);
5270     if (!webviewController) {
5271         return result;
5272     }
5273     webviewController->SetPrintBackground(printBackgroundEnabled);
5274     return result;
5275 }
5276 
GetPrintBackground(napi_env env, napi_callback_info info)5277 napi_value NapiWebviewController::GetPrintBackground(napi_env env, napi_callback_info info)
5278 {
5279     napi_value result = nullptr;
5280     WebviewController *webviewController = GetWebviewController(env, info);
5281 
5282     if (!webviewController) {
5283         return result;
5284     }
5285 
5286     bool printBackgroundEnabled = webviewController->GetPrintBackground();
5287     NAPI_CALL(env, napi_get_boolean(env, printBackgroundEnabled, &result));
5288     return result;
5289 }
5290 
SetWebSchemeHandler(napi_env env, napi_callback_info info)5291 napi_value NapiWebviewController::SetWebSchemeHandler(napi_env env, napi_callback_info info)
5292 {
5293     size_t argc = 2;
5294     napi_value argv[2] = {0};
5295     napi_value thisVar = nullptr;
5296     void* data = nullptr;
5297     napi_get_cb_info(env, info, &argc, argv, &thisVar, &data);
5298 
5299     WebviewController *webviewController = nullptr;
5300     NAPI_CALL(env, napi_unwrap(env, thisVar, (void **)&webviewController));
5301     if (webviewController == nullptr || !webviewController->IsInit()) {
5302         BusinessError::ThrowErrorByErrcode(env, INIT_ERROR);
5303         WVLOG_E("create message port failed, napi unwrap webviewController failed");
5304         return nullptr;
5305     }
5306 
5307     std::string scheme = "";
5308     if (!NapiParseUtils::ParseString(env, argv[0], scheme)) {
5309         WVLOG_E("NapiWebviewController::SetWebSchemeHandler parse scheme failed");
5310         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5311             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "scheme", "string"));
5312         return nullptr;
5313     }
5314 
5315     WebSchemeHandler* handler = nullptr;
5316     napi_value obj = argv[1];
5317     napi_unwrap(env, obj, (void**)&handler);
5318     if (!handler) {
5319         WVLOG_E("NapiWebviewController::SetWebSchemeHandler handler is null");
5320         return nullptr;
5321     }
5322     napi_create_reference(env, obj, 1, &handler->delegate_);
5323 
5324     if (!webviewController->SetWebSchemeHandler(scheme.c_str(), handler)) {
5325         WVLOG_E("NapiWebviewController::SetWebSchemeHandler failed");
5326     }
5327     return nullptr;
5328 }
5329 
ClearWebSchemeHandler(napi_env env, napi_callback_info info)5330 napi_value NapiWebviewController::ClearWebSchemeHandler(napi_env env, napi_callback_info info)
5331 {
5332     napi_value result = nullptr;
5333     WebviewController *webviewController = GetWebviewController(env, info);
5334     if (!webviewController) {
5335         return nullptr;
5336     }
5337 
5338     int32_t ret = webviewController->ClearWebSchemeHandler();
5339     if (ret != 0) {
5340         WVLOG_E("NapiWebviewController::ClearWebSchemeHandler failed");
5341     }
5342     NAPI_CALL(env, napi_get_undefined(env, &result));
5343     return result;
5344 }
5345 
SetServiceWorkerWebSchemeHandler( napi_env env, napi_callback_info info)5346 napi_value NapiWebviewController::SetServiceWorkerWebSchemeHandler(
5347     napi_env env, napi_callback_info info)
5348 {
5349     size_t argc = 2;
5350     napi_value argv[2] = {0};
5351     napi_value thisVar = nullptr;
5352     void* data = nullptr;
5353     napi_get_cb_info(env, info, &argc, argv, &thisVar, &data);
5354 
5355     std::string scheme = "";
5356     if (!NapiParseUtils::ParseString(env, argv[0], scheme)) {
5357         WVLOG_E("NapiWebviewController::SetWebSchemeHandler parse scheme failed");
5358         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5359             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "scheme", "string"));
5360         return nullptr;
5361     }
5362 
5363     WebSchemeHandler* handler = nullptr;
5364     napi_value obj = argv[1];
5365     napi_unwrap(env, obj, (void**)&handler);
5366     if (!handler) {
5367         WVLOG_E("NapiWebviewController::SetServiceWorkerWebSchemeHandler handler is null");
5368         return nullptr;
5369     }
5370     napi_create_reference(env, obj, 1, &handler->delegate_);
5371 
5372     if (!WebviewController::SetWebServiveWorkerSchemeHandler(
5373         scheme.c_str(), handler)) {
5374         WVLOG_E("NapiWebviewController::SetWebSchemeHandler failed");
5375     }
5376     return nullptr;
5377 }
5378 
ClearServiceWorkerWebSchemeHandler( napi_env env, napi_callback_info info)5379 napi_value NapiWebviewController::ClearServiceWorkerWebSchemeHandler(
5380     napi_env env, napi_callback_info info)
5381 {
5382     int32_t ret = WebviewController::ClearWebServiceWorkerSchemeHandler();
5383     if (ret != 0) {
5384         WVLOG_E("ClearServiceWorkerWebSchemeHandler ret=%{public}d", ret);
5385         return nullptr;
5386     }
5387     return nullptr;
5388 }
5389 
EnableIntelligentTrackingPrevention( napi_env env, napi_callback_info info)5390 napi_value NapiWebviewController::EnableIntelligentTrackingPrevention(
5391     napi_env env, napi_callback_info info)
5392 {
5393     WVLOG_I("enable/disable intelligent tracking prevention.");
5394     napi_value result = nullptr;
5395     napi_value thisVar = nullptr;
5396     size_t argc = INTEGER_ONE;
5397     napi_value argv[INTEGER_ONE] = { 0 };
5398 
5399     NAPI_CALL(env, napi_get_undefined(env, &result));
5400     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5401     if (argc != INTEGER_ONE) {
5402         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5403             "BusinessError 401: Parameter error. The number of params must be one.");
5404         return result;
5405     }
5406 
5407     bool enabled = false;
5408     if (!NapiParseUtils::ParseBoolean(env, argv[INTEGER_ZERO], enabled)) {
5409         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5410             "BusinessError 401: Parameter error. The type of 'enable' must be boolean.");
5411         return result;
5412     }
5413 
5414     WebviewController *webviewController = GetWebviewController(env, info);
5415     if (!webviewController) {
5416         return result;
5417     }
5418     webviewController->EnableIntelligentTrackingPrevention(enabled);
5419     return result;
5420 }
5421 
IsIntelligentTrackingPreventionEnabled( napi_env env, napi_callback_info info)5422 napi_value NapiWebviewController::IsIntelligentTrackingPreventionEnabled(
5423     napi_env env, napi_callback_info info)
5424 {
5425     WVLOG_I("get intelligent tracking prevention enabled value.");
5426     napi_value result = nullptr;
5427     WebviewController *webviewController = GetWebviewController(env, info);
5428 
5429     if (!webviewController) {
5430         return result;
5431     }
5432 
5433     bool enabled = webviewController->
5434         IsIntelligentTrackingPreventionEnabled();
5435     NAPI_CALL(env, napi_get_boolean(env, enabled, &result));
5436     return result;
5437 }
5438 
GetHostList(napi_env env, napi_value array, std::vector<std::string>& hosts)5439 bool GetHostList(napi_env env, napi_value array, std::vector<std::string>& hosts)
5440 {
5441     uint32_t arrayLen = 0;
5442     napi_get_array_length(env, array, &arrayLen);
5443     if (arrayLen == 0) {
5444         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5445             "BusinessError 401: Parameter error. The array length must be greater than 0.");
5446         return false;
5447     }
5448 
5449     for (uint32_t i = 0; i < arrayLen; i++) {
5450         napi_value hostItem = nullptr;
5451         napi_get_element(env, array, i, &hostItem);
5452 
5453         size_t hostLen = 0;
5454         napi_get_value_string_utf8(env, hostItem, nullptr, 0, &hostLen);
5455         if (hostLen == 0 || hostLen > UINT_MAX) {
5456             WVLOG_E("hostitem length is invalid");
5457             return false;
5458         }
5459 
5460         char host[hostLen + 1];
5461         int retCode = memset_s(host, sizeof(host), 0, hostLen + 1);
5462         if (retCode < 0) {
5463             WVLOG_E("memset_s failed, retCode=%{public}d", retCode);
5464             return false;
5465         }
5466         napi_get_value_string_utf8(env, hostItem, host, sizeof(host), &hostLen);
5467         std::string hostStr(host);
5468         hosts.emplace_back(hostStr);
5469     }
5470     return true;
5471 }
5472 
AddIntelligentTrackingPreventionBypassingList( napi_env env, napi_callback_info info)5473 napi_value NapiWebviewController::AddIntelligentTrackingPreventionBypassingList(
5474     napi_env env, napi_callback_info info)
5475 {
5476     WVLOG_I("Add intelligent tracking prevention bypassing list.");
5477     napi_value result = nullptr;
5478     napi_value thisVar = nullptr;
5479     size_t argc = INTEGER_ONE;
5480     napi_value argv[INTEGER_ONE] = { 0 };
5481     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5482     if (argc != INTEGER_ONE) {
5483         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5484             "BusinessError 401: Parameter error. The number of params must be one.");
5485         return result;
5486     }
5487 
5488     bool isArray = false;
5489     NAPI_CALL(env, napi_is_array(env, argv[INTEGER_ZERO], &isArray));
5490     if (!isArray) {
5491         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5492             "BusinessError 401: Parameter error. The type of 'hostList' must be string array.");
5493         return result;
5494     }
5495 
5496     std::vector<std::string> hosts;
5497     if (!GetHostList(env, argv[INTEGER_ZERO], hosts)) {
5498         WVLOG_E("get host list failed, GetHostList fail");
5499         return result;
5500     }
5501 
5502     NWebHelper::Instance().AddIntelligentTrackingPreventionBypassingList(hosts);
5503     NAPI_CALL(env, napi_get_undefined(env, &result));
5504     return result;
5505 }
5506 
RemoveIntelligentTrackingPreventionBypassingList( napi_env env, napi_callback_info info)5507 napi_value NapiWebviewController::RemoveIntelligentTrackingPreventionBypassingList(
5508     napi_env env, napi_callback_info info)
5509 {
5510     WVLOG_I("Remove intelligent tracking prevention bypassing list.");
5511     napi_value result = nullptr;
5512     napi_value thisVar = nullptr;
5513     size_t argc = INTEGER_ONE;
5514     napi_value argv[INTEGER_ONE] = { 0 };
5515     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5516     if (argc != INTEGER_ONE) {
5517         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5518             "BusinessError 401: Parameter error. The number of params must be one.");
5519         return result;
5520     }
5521 
5522     bool isArray = false;
5523     NAPI_CALL(env, napi_is_array(env, argv[INTEGER_ZERO], &isArray));
5524     if (!isArray) {
5525         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5526             "BusinessError 401: Parameter error. The type of 'hostList' must be string array.");
5527         return result;
5528     }
5529 
5530     std::vector<std::string> hosts;
5531     if (!GetHostList(env, argv[INTEGER_ZERO], hosts)) {
5532         WVLOG_E("get host list failed, GetHostList fail");
5533         return result;
5534     }
5535 
5536     NWebHelper::Instance().RemoveIntelligentTrackingPreventionBypassingList(hosts);
5537     NAPI_CALL(env, napi_get_undefined(env, &result));
5538     return result;
5539 }
5540 
ClearIntelligentTrackingPreventionBypassingList( napi_env env, napi_callback_info info)5541 napi_value NapiWebviewController::ClearIntelligentTrackingPreventionBypassingList(
5542     napi_env env, napi_callback_info info)
5543 {
5544     napi_value result = nullptr;
5545     WVLOG_I("Clear intelligent tracking prevention bypassing list.");
5546     NWebHelper::Instance().ClearIntelligentTrackingPreventionBypassingList();
5547     NAPI_CALL(env, napi_get_undefined(env, &result));
5548     return result;
5549 }
5550 
GetDefaultUserAgent(napi_env env, napi_callback_info info)5551 napi_value NapiWebviewController::GetDefaultUserAgent(napi_env env, napi_callback_info info)
5552 {
5553     WVLOG_I("Get the default user agent.");
5554     napi_value result = nullptr;
5555 
5556     std::string userAgent = NWebHelper::Instance().GetDefaultUserAgent();
5557     NAPI_CALL(env, napi_create_string_utf8(env, userAgent.c_str(), userAgent.length(), &result));
5558     return result;
5559 }
5560 
PauseAllTimers(napi_env env, napi_callback_info info)5561 napi_value NapiWebviewController::PauseAllTimers(napi_env env, napi_callback_info info)
5562 {
5563     napi_value result = nullptr;
5564     NWebHelper::Instance().PauseAllTimers();
5565     NAPI_CALL(env, napi_get_undefined(env, &result));
5566     return result;
5567 }
5568 
ResumeAllTimers(napi_env env, napi_callback_info info)5569 napi_value NapiWebviewController::ResumeAllTimers(napi_env env, napi_callback_info info)
5570 {
5571     napi_value result = nullptr;
5572     NWebHelper::Instance().ResumeAllTimers();
5573     NAPI_CALL(env, napi_get_undefined(env, &result));
5574     return result;
5575 }
5576 
StartCamera(napi_env env, napi_callback_info info)5577 napi_value NapiWebviewController::StartCamera(napi_env env, napi_callback_info info)
5578 {
5579     napi_value result = nullptr;
5580     NAPI_CALL(env, napi_get_undefined(env, &result));
5581     WebviewController* webviewController = GetWebviewController(env, info);
5582     if (!webviewController) {
5583         return result;
5584     }
5585     webviewController->StartCamera();
5586 
5587     return result;
5588 }
5589 
StopCamera(napi_env env, napi_callback_info info)5590 napi_value NapiWebviewController::StopCamera(napi_env env, napi_callback_info info)
5591 {
5592     napi_value result = nullptr;
5593     NAPI_CALL(env, napi_get_undefined(env, &result));
5594     WebviewController* webviewController = GetWebviewController(env, info);
5595     if (!webviewController) {
5596         return result;
5597     }
5598     webviewController->StopCamera();
5599 
5600     return result;
5601 }
5602 
CloseCamera(napi_env env, napi_callback_info info)5603 napi_value NapiWebviewController::CloseCamera(napi_env env, napi_callback_info info)
5604 {
5605     napi_value result = nullptr;
5606     NAPI_CALL(env, napi_get_undefined(env, &result));
5607     WebviewController* webviewController = GetWebviewController(env, info);
5608     if (!webviewController) {
5609         return result;
5610     }
5611     webviewController->CloseCamera();
5612 
5613     return result;
5614 }
5615 
OnCreateNativeMediaPlayer(napi_env env, napi_callback_info info)5616 napi_value NapiWebviewController::OnCreateNativeMediaPlayer(napi_env env, napi_callback_info info)
5617 {
5618     WVLOG_D("put on_create_native_media_player callback");
5619 
5620     size_t argc = INTEGER_ONE;
5621     napi_value value = nullptr;
5622     napi_value argv[INTEGER_ONE];
5623     napi_get_cb_info(env, info, &argc, argv, &value, nullptr);
5624     if (argc != INTEGER_ONE) {
5625         WVLOG_E("arg count %{public}zu is not equal to 1", argc);
5626         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5627         return nullptr;
5628     }
5629 
5630     napi_valuetype valueType = napi_undefined;
5631     napi_typeof(env, argv[INTEGER_ZERO], &valueType);
5632     if (valueType != napi_function) {
5633         WVLOG_E("arg type is invalid");
5634         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5635         return nullptr;
5636     }
5637 
5638     napi_ref callback = nullptr;
5639     napi_create_reference(env, argv[INTEGER_ZERO], INTEGER_ONE, &callback);
5640     if (!callback) {
5641         WVLOG_E("failed to create reference for callback");
5642         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5643         return nullptr;
5644     }
5645 
5646     WebviewController* webviewController = GetWebviewController(env, info);
5647     if (!webviewController || !webviewController->IsInit()) {
5648         WVLOG_E("webview controller is null or not init");
5649         napi_delete_reference(env, callback);
5650         return nullptr;
5651     }
5652 
5653     webviewController->OnCreateNativeMediaPlayer(env, std::move(callback));
5654     return nullptr;
5655 }
5656 
SetRenderProcessMode( napi_env env, napi_callback_info info)5657 napi_value NapiWebviewController::SetRenderProcessMode(
5658     napi_env env, napi_callback_info info)
5659 {
5660     WVLOG_I("set render process mode.");
5661     napi_value result = nullptr;
5662     napi_value thisVar = nullptr;
5663     size_t argc = INTEGER_ONE;
5664     napi_value argv[INTEGER_ONE] = { 0 };
5665 
5666     NAPI_CALL(env, napi_get_undefined(env, &result));
5667     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5668     if (argc != INTEGER_ONE) {
5669         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5670             "BusinessError 401: Parameter error. The number of params must be one.");
5671         return result;
5672     }
5673 
5674     int32_t mode = 0;
5675     if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_ZERO], mode)) {
5676         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5677             "BusinessError 401: Parameter error. The type of 'mode' must be int.");
5678         return result;
5679     }
5680 
5681     NWebHelper::Instance().SetRenderProcessMode(
5682         static_cast<RenderProcessMode>(mode));
5683 
5684     return result;
5685 }
5686 
GetRenderProcessMode( napi_env env, napi_callback_info info)5687 napi_value NapiWebviewController::GetRenderProcessMode(
5688     napi_env env, napi_callback_info info)
5689 {
5690     WVLOG_I("get render mode.");
5691     napi_value result = nullptr;
5692 
5693     int32_t mode = static_cast<int32_t>(NWebHelper::Instance().GetRenderProcessMode());
5694     NAPI_CALL(env, napi_create_int32(env, mode, &result));
5695     return result;
5696 }
5697 
PrecompileJavaScript(napi_env env, napi_callback_info info)5698 napi_value NapiWebviewController::PrecompileJavaScript(napi_env env, napi_callback_info info)
5699 {
5700     napi_value thisVar = nullptr;
5701     napi_value result = nullptr;
5702     size_t argc = INTEGER_THREE;
5703     napi_value argv[INTEGER_THREE] = {0};
5704     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5705     if (argc != INTEGER_THREE) {
5706         WVLOG_E("BusinessError: 401. Args count of 'PrecompileJavaScript' must be 3.");
5707         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5708         return result;
5709     }
5710 
5711     WebviewController* webviewController = GetWebviewController(env, info);
5712     if (!webviewController) {
5713         WVLOG_E("PrecompileJavaScript: init webview controller error.");
5714         return result;
5715     }
5716 
5717     std::string url;
5718     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], url) || url.empty()) {
5719         WVLOG_E("BusinessError: 401. The type of 'url' must be string.");
5720         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5721         return result;
5722     }
5723 
5724     std::string script;
5725     bool parseResult = webviewController->ParseScriptContent(env, argv[INTEGER_ONE], script);
5726     if (!parseResult) {
5727         WVLOG_E("BusinessError: 401. The type of 'script' must be string or Uint8Array.");
5728         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5729         return result;
5730     }
5731 
5732     auto cacheOptions = webviewController->ParseCacheOptions(env, argv[INTEGER_TWO]);
5733 
5734     napi_deferred deferred = nullptr;
5735     napi_value promise = nullptr;
5736     napi_create_promise(env, &deferred, &promise);
5737     if (promise && deferred) {
5738         webviewController->PrecompileJavaScriptPromise(env, deferred, url, script, cacheOptions);
5739         return promise;
5740     }
5741 
5742     return promise;
5743 }
5744 
EnableBackForwardCache(napi_env env, napi_callback_info info)5745 napi_value NapiWebviewController::EnableBackForwardCache(napi_env env, napi_callback_info info)
5746 {
5747     napi_value thisVar = nullptr;
5748     napi_value result = nullptr;
5749     size_t argc = INTEGER_ONE;
5750     napi_value argv[INTEGER_ONE] = { 0 };
5751     napi_get_undefined(env, &result);
5752     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5753     if (argc != INTEGER_ONE) {
5754         WVLOG_E("EnalbeBackForwardCache: wrong number of params.");
5755         NWebHelper::Instance().EnableBackForwardCache(false, false);
5756         NAPI_CALL(env, napi_get_undefined(env, &result));
5757         return result;
5758     }
5759 
5760     bool nativeEmbed = false;
5761     bool mediaTakeOver = false;
5762     napi_value embedObj = nullptr;
5763     napi_value mediaObj = nullptr;
5764     if (napi_get_named_property(env, argv[INTEGER_ZERO], "nativeEmbed", &embedObj) == napi_ok) {
5765         if (!NapiParseUtils::ParseBoolean(env, embedObj, nativeEmbed)) {
5766             nativeEmbed = false;
5767         }
5768     }
5769 
5770     if (napi_get_named_property(env, argv[INTEGER_ZERO], "mediaTakeOver", &mediaObj) == napi_ok) {
5771         if (!NapiParseUtils::ParseBoolean(env, mediaObj, mediaTakeOver)) {
5772             mediaTakeOver = false;
5773         }
5774     }
5775 
5776     NWebHelper::Instance().EnableBackForwardCache(nativeEmbed, mediaTakeOver);
5777     NAPI_CALL(env, napi_get_undefined(env, &result));
5778     return result;
5779 }
5780 
SetBackForwardCacheOptions(napi_env env, napi_callback_info info)5781 napi_value NapiWebviewController::SetBackForwardCacheOptions(napi_env env, napi_callback_info info)
5782 {
5783     napi_value thisVar = nullptr;
5784     napi_value result = nullptr;
5785     size_t argc = INTEGER_ONE;
5786     napi_value argv[INTEGER_ONE] = { 0 };
5787     napi_get_undefined(env, &result);
5788     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5789     WebviewController* webviewController = GetWebviewController(env, info);
5790     if (!webviewController) {
5791         WVLOG_E("SetBackForwardCacheOptions: Init webview controller error.");
5792         return result;
5793     }
5794 
5795     if (argc != INTEGER_ONE) {
5796         WVLOG_E("SetBackForwardCacheOptions: wrong number of params.");
5797         webviewController->SetBackForwardCacheOptions(
5798             BFCACHE_DEFAULT_SIZE, BFCACHE_DEFAULT_TIMETOLIVE);
5799         NAPI_CALL(env, napi_get_undefined(env, &result));
5800         return result;
5801     }
5802 
5803     int32_t size = BFCACHE_DEFAULT_SIZE;
5804     int32_t timeToLive = BFCACHE_DEFAULT_TIMETOLIVE;
5805     napi_value sizeObj = nullptr;
5806     napi_value timeToLiveObj = nullptr;
5807     if (napi_get_named_property(env, argv[INTEGER_ZERO], "size", &sizeObj) == napi_ok) {
5808         if (!NapiParseUtils::ParseInt32(env, sizeObj, size)) {
5809             size = BFCACHE_DEFAULT_SIZE;
5810         }
5811     }
5812 
5813     if (napi_get_named_property(env, argv[INTEGER_ZERO], "timeToLive", &timeToLiveObj) == napi_ok) {
5814         if (!NapiParseUtils::ParseInt32(env, timeToLiveObj, timeToLive)) {
5815             timeToLive = BFCACHE_DEFAULT_TIMETOLIVE;
5816         }
5817     }
5818 
5819     webviewController->SetBackForwardCacheOptions(size, timeToLive);
5820     NAPI_CALL(env, napi_get_undefined(env, &result));
5821     return result;
5822 }
5823 
WarmupServiceWorker(napi_env env, napi_callback_info info)5824 napi_value NapiWebviewController::WarmupServiceWorker(napi_env env, napi_callback_info info)
5825 {
5826     napi_value thisVar = nullptr;
5827     napi_value result = nullptr;
5828     size_t argc = INTEGER_ONE;
5829     napi_value argv[INTEGER_ONE] = { 0 };
5830     napi_get_undefined(env, &result);
5831     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5832     if (argc != INTEGER_ONE) {
5833         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5834         return result;
5835     }
5836 
5837     std::string url;
5838     if (!ParsePrepareUrl(env, argv[INTEGER_ZERO], url)) {
5839         BusinessError::ThrowErrorByErrcode(env, INVALID_URL);
5840         return result;
5841     }
5842 
5843     NWebHelper::Instance().WarmupServiceWorker(url);
5844     return result;
5845 }
5846 
InjectOfflineResources(napi_env env, napi_callback_info info)5847 napi_value NapiWebviewController::InjectOfflineResources(napi_env env, napi_callback_info info)
5848 {
5849     napi_value thisVar = nullptr;
5850     napi_value result = nullptr;
5851     size_t argc = INTEGER_ONE;
5852     napi_value argv[INTEGER_ONE] = {0};
5853     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5854     if (argc != INTEGER_ONE) {
5855         WVLOG_E("BusinessError: 401. Args count of 'InjectOfflineResource' must be 1.");
5856         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5857         return result;
5858     }
5859 
5860     napi_value resourcesList = argv[INTEGER_ZERO];
5861     bool isArray = false;
5862     napi_is_array(env, resourcesList, &isArray);
5863     if (!isArray) {
5864         WVLOG_E("BusinessError: 401. The type of 'resourceMaps' must be Array");
5865         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5866         return result;
5867     }
5868 
5869     AddResourcesToMemoryCache(env, info, resourcesList);
5870     return result;
5871 }
5872 
AddResourcesToMemoryCache(napi_env env, napi_callback_info info, napi_value& resourcesList)5873 void NapiWebviewController::AddResourcesToMemoryCache(napi_env env,
5874                                                       napi_callback_info info,
5875                                                       napi_value& resourcesList)
5876 {
5877     uint32_t resourcesCount = 0;
5878     napi_get_array_length(env, resourcesList, &resourcesCount);
5879 
5880     if (resourcesCount > MAX_RESOURCES_COUNT || resourcesCount == 0) {
5881         WVLOG_E("BusinessError: 401. The size of 'resourceMaps' must less than %{public}zu and not 0",
5882             MAX_RESOURCES_COUNT);
5883         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5884         return;
5885     }
5886 
5887     for (uint32_t i = 0 ; i < resourcesCount ; i++) {
5888         napi_value urlListObj = nullptr;
5889         napi_value resourceObj = nullptr;
5890         napi_value headersObj = nullptr;
5891         napi_value typeObj = nullptr;
5892         napi_value obj = nullptr;
5893 
5894         napi_create_array(env, &headersObj);
5895         napi_create_array(env, &urlListObj);
5896 
5897         napi_get_element(env, resourcesList, i, &obj);
5898         if ((napi_get_named_property(env, obj, "urlList", &urlListObj) != napi_ok) ||
5899             (napi_get_named_property(env, obj, "resource", &resourceObj) != napi_ok) ||
5900             (napi_get_named_property(env, obj, "responseHeaders", &headersObj) != napi_ok) ||
5901             (napi_get_named_property(env, obj, "type", &typeObj) != napi_ok)) {
5902             WVLOG_E("InjectOfflineResources: parse params from resource map failed.");
5903             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5904             continue;
5905         }
5906 
5907         OfflineResourceValue resourceValue;
5908         resourceValue.urlList = urlListObj;
5909         resourceValue.resource = resourceObj;
5910         resourceValue.responseHeaders = headersObj;
5911         resourceValue.type = typeObj;
5912         AddResourceItemToMemoryCache(env, info, resourceValue);
5913     }
5914 }
5915 
AddResourceItemToMemoryCache(napi_env env, napi_callback_info info, OfflineResourceValue resourceValue)5916 void NapiWebviewController::AddResourceItemToMemoryCache(napi_env env,
5917                                                          napi_callback_info info,
5918                                                          OfflineResourceValue resourceValue)
5919 {
5920     WebviewController* webviewController = GetWebviewController(env, info);
5921     if (!webviewController) {
5922         WVLOG_E("InjectOfflineResource: init webview controller error.");
5923         return;
5924     }
5925 
5926     std::vector<std::string> urlList;
5927     ParseURLResult result = webviewController->ParseURLList(env, resourceValue.urlList, urlList);
5928     if (result != ParseURLResult::OK) {
5929         auto errCode = result == ParseURLResult::FAILED ? PARAM_CHECK_ERROR : INVALID_URL;
5930         if (errCode == PARAM_CHECK_ERROR) {
5931             WVLOG_E("BusinessError: 401. The type of 'urlList' must be Array of string.");
5932         }
5933         BusinessError::ThrowErrorByErrcode(env, errCode);
5934         return;
5935     }
5936 
5937     std::vector<uint8_t> resource = webviewController->ParseUint8Array(env, resourceValue.resource);
5938     if (resource.empty() || resource.size() > MAX_RESOURCE_SIZE) {
5939         WVLOG_E("BusinessError: 401. The type of 'resource' must be Uint8Array. "
5940             "'resource' size must less than %{public}zu and must not be empty.", MAX_RESOURCE_SIZE);
5941         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5942         return;
5943     }
5944 
5945     std::map<std::string, std::string> responseHeaders;
5946     if (!webviewController->ParseResponseHeaders(env, resourceValue.responseHeaders, responseHeaders)) {
5947         WVLOG_E("BusinessError: 401. The type of 'responseHeaders' must be Array of 'WebHeader'.");
5948         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5949         return;
5950     }
5951 
5952     uint32_t type = 0;
5953     if (!NapiParseUtils::ParseUint32(env, resourceValue.type, type)) {
5954         WVLOG_E("BusinessError: 401. The type of 'type' must be one kind of 'OfflineResourceType'.");
5955         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
5956         return;
5957     }
5958 
5959     webviewController->InjectOfflineResource(urlList, resource, responseHeaders, type);
5960 }
5961 
SetHostIP(napi_env env, napi_callback_info info)5962 napi_value NapiWebviewController::SetHostIP(napi_env env, napi_callback_info info)
5963 {
5964     napi_value thisVar = nullptr;
5965     napi_value result = nullptr;
5966     size_t argc = INTEGER_THREE;
5967     napi_value argv[INTEGER_THREE] = { 0 };
5968     std::string hostName;
5969     std::string address;
5970     int32_t aliveTime = INTEGER_ZERO;
5971 
5972     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
5973     if (argc != INTEGER_THREE) {
5974         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5975             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "three"));
5976         return result;
5977     }
5978 
5979     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], hostName) ||
5980         !NapiParseUtils::ParseString(env, argv[INTEGER_ONE], address) ||
5981         !NapiParseUtils::ParseInt32(env, argv[INTEGER_TWO], aliveTime) ||
5982         aliveTime <= 0) {
5983         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR, ParamCheckErrorMsgTemplate::PARAM_TYEPS_ERROR);
5984         return result;
5985     }
5986 
5987     if (!ParseIP(env, argv[INTEGER_ONE], address)) {
5988         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
5989             "BusinessError 401: IP address error.");
5990         return result;
5991     }
5992 
5993     NWebHelper::Instance().SetHostIP(hostName, address, aliveTime);
5994     NAPI_CALL(env, napi_get_undefined(env, &result));
5995 
5996     return result;
5997 }
5998 
ClearHostIP(napi_env env, napi_callback_info info)5999 napi_value NapiWebviewController::ClearHostIP(napi_env env, napi_callback_info info)
6000 {
6001     napi_value thisVar = nullptr;
6002     napi_value result = nullptr;
6003     size_t argc = INTEGER_ONE;
6004     napi_value argv[INTEGER_ONE] = { 0 };
6005     std::string hostName;
6006 
6007     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
6008     if (argc != INTEGER_ONE) {
6009         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6010             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
6011         return result;
6012     }
6013 
6014     if (!NapiParseUtils::ParseString(env, argv[INTEGER_ZERO], hostName)) {
6015         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6016             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "hostName", "string"));
6017         return result;
6018     }
6019 
6020     NWebHelper::Instance().ClearHostIP(hostName);
6021     NAPI_CALL(env, napi_get_undefined(env, &result));
6022     return result;
6023 }
6024 
EnableWholeWebPageDrawing( napi_env env, napi_callback_info info)6025 napi_value NapiWebviewController::EnableWholeWebPageDrawing(
6026     napi_env env, napi_callback_info info)
6027 {
6028     napi_value result = nullptr;
6029     NWebHelper::Instance().EnableWholeWebPageDrawing();
6030     NAPI_CALL(env, napi_get_undefined(env, &result));
6031     return result;
6032 }
6033 
EnableAdsBlock( napi_env env, napi_callback_info info)6034 napi_value NapiWebviewController::EnableAdsBlock(
6035     napi_env env, napi_callback_info info)
6036 {
6037     napi_value result = nullptr;
6038     napi_value thisVar = nullptr;
6039     size_t argc = INTEGER_ONE;
6040     napi_value argv[INTEGER_ONE] = { 0 };
6041 
6042     NAPI_CALL(env, napi_get_undefined(env, &result));
6043     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
6044     if (argc != INTEGER_ONE) {
6045         WVLOG_E("EnableAdsBlock: args count is not allowed.");
6046         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6047             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
6048         return result;
6049     }
6050 
6051     bool enabled = false;
6052     if (!NapiParseUtils::ParseBoolean(env, argv[INTEGER_ZERO], enabled)) {
6053         WVLOG_E("EnableAdsBlock: the given enabled is not allowed.");
6054         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6055             "BusinessError 401: Parameter error. The type of 'enable' must be boolean.");
6056         return result;
6057     }
6058 
6059     WebviewController *webviewController = GetWebviewController(env, info);
6060     if (!webviewController) {
6061         WVLOG_E("EnableAdsBlock: init webview controller error.");
6062         return result;
6063     }
6064 
6065     WVLOG_I("EnableAdsBlock: %{public}s", (enabled ? "true" : "false"));
6066     webviewController->EnableAdsBlock(enabled);
6067     return result;
6068 }
6069 
IsAdsBlockEnabled(napi_env env, napi_callback_info info)6070 napi_value NapiWebviewController::IsAdsBlockEnabled(napi_env env, napi_callback_info info)
6071 {
6072     napi_value result = nullptr;
6073     WebviewController *webviewController = GetWebviewController(env, info);
6074     if (!webviewController) {
6075         return nullptr;
6076     }
6077 
6078     bool isAdsBlockEnabled = webviewController->IsAdsBlockEnabled();
6079     NAPI_CALL(env, napi_get_boolean(env, isAdsBlockEnabled, &result));
6080     return result;
6081 }
6082 
IsAdsBlockEnabledForCurPage(napi_env env, napi_callback_info info)6083 napi_value NapiWebviewController::IsAdsBlockEnabledForCurPage(napi_env env, napi_callback_info info)
6084 {
6085     napi_value result = nullptr;
6086     WebviewController *webviewController = GetWebviewController(env, info);
6087     if (!webviewController) {
6088         return nullptr;
6089     }
6090 
6091     bool isAdsBlockEnabledForCurPage = webviewController->IsAdsBlockEnabledForCurPage();
6092     NAPI_CALL(env, napi_get_boolean(env, isAdsBlockEnabledForCurPage, &result));
6093     return result;
6094 }
6095 
GetSurfaceId(napi_env env, napi_callback_info info)6096 napi_value NapiWebviewController::GetSurfaceId(napi_env env, napi_callback_info info)
6097 {
6098     napi_value result = nullptr;
6099     WebviewController *webviewController = GetWebviewController(env, info);
6100     if (!webviewController) {
6101         return nullptr;
6102     }
6103 
6104     std::string surfaceId = webviewController->GetSurfaceId();
6105     napi_create_string_utf8(env, surfaceId.c_str(), surfaceId.length(), &result);
6106     return result;
6107 }
6108 
UpdateInstanceId(napi_env env, napi_callback_info info)6109 napi_value NapiWebviewController::UpdateInstanceId(napi_env env, napi_callback_info info)
6110 {
6111     WVLOG_D("Instance changed");
6112     napi_value result = nullptr;
6113     napi_value thisVar = nullptr;
6114     size_t argc = INTEGER_ONE;
6115     napi_value argv[INTEGER_ONE] = { 0 };
6116 
6117     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
6118     if (argc != INTEGER_ONE) {
6119         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
6120         return result;
6121     }
6122 
6123     int32_t newId = 0;
6124     if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_ZERO], newId)) {
6125         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
6126         return result;
6127     }
6128 
6129     WebviewController *webviewController = nullptr;
6130     napi_status status = napi_unwrap(env, thisVar, (void **)&webviewController);
6131     if ((!webviewController) || (status != napi_ok) || !webviewController->IsInit()) {
6132         return result;
6133     }
6134 
6135     webviewController->UpdateInstanceId(newId);
6136 
6137     NAPI_CALL(env, napi_get_undefined(env, &result));
6138     return result;
6139 }
6140 
SetUrlTrustList(napi_env env, napi_callback_info info)6141 napi_value NapiWebviewController::SetUrlTrustList(napi_env env, napi_callback_info info)
6142 {
6143     WVLOG_D("SetUrlTrustList invoked");
6144 
6145     napi_value result = nullptr;
6146     NAPI_CALL(env, napi_get_undefined(env, &result));
6147 
6148     napi_value thisVar = nullptr;
6149     size_t argc = INTEGER_ONE;
6150     napi_value argv[INTEGER_ONE] = { 0 };
6151     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
6152     if (argc != INTEGER_ONE) {
6153         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6154             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
6155         return result;
6156     }
6157 
6158     std::string urlTrustList;
6159     if (!NapiParseUtils::ParseString(env, argv[0], urlTrustList)) {
6160         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6161             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "urlTrustList", "string"));
6162         return result;
6163     }
6164     if (urlTrustList.size() > MAX_URL_TRUST_LIST_STR_LEN) {
6165         WVLOG_E("EnableAdsBlock: url trust list len is too large.");
6166         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
6167         return result;
6168     }
6169 
6170     WebviewController* webviewController = GetWebviewController(env, info);
6171     if (!webviewController) {
6172         WVLOG_E("webview controller is null or not init");
6173         return result;
6174     }
6175 
6176     std::string detailMsg;
6177     ErrCode ret = webviewController->SetUrlTrustList(urlTrustList, detailMsg);
6178     if (ret != NO_ERROR) {
6179         WVLOG_E("SetUrlTrustList failed, error code: %{public}d", ret);
6180         BusinessError::ThrowErrorByErrcode(env, ret,
6181             NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_DETAIL_ERROR_MSG, detailMsg.c_str()));
6182         return result;
6183     }
6184     return result;
6185 }
6186 
CreateWebPageSnapshotResultCallback( napi_env env, napi_ref jsCallback, bool check, int32_t inputWidth, int32_t inputHeight)6187 WebSnapshotCallback CreateWebPageSnapshotResultCallback(
6188     napi_env env, napi_ref jsCallback, bool check, int32_t inputWidth, int32_t inputHeight)
6189 {
6190     return
6191         [env, jCallback = std::move(jsCallback), check, inputWidth, inputHeight](
6192             const char *returnId, bool returnStatus, float radio, void *returnData,
6193             int returnWidth, int returnHeight) {
6194             WVLOG_I("WebPageSnapshot return napi callback");
6195             napi_value jsResult = nullptr;
6196             napi_create_object(env, &jsResult);
6197 
6198             napi_value jsPixelMap = nullptr;
6199             Media::InitializationOptions opt;
6200             opt.size.width = static_cast<int32_t>(returnWidth);
6201             opt.size.height = static_cast<int32_t>(returnHeight);
6202             opt.pixelFormat = Media::PixelFormat::RGBA_8888;
6203             opt.alphaType = Media::AlphaType::IMAGE_ALPHA_TYPE_OPAQUE;
6204             opt.editable = true;
6205             auto pixelMap = Media::PixelMap::Create(opt);
6206             if (pixelMap != nullptr) {
6207                 uint64_t stride = static_cast<uint64_t>(returnWidth) << 2;
6208                 uint64_t bufferSize = stride * static_cast<uint64_t>(returnHeight);
6209                 pixelMap->WritePixels(static_cast<const uint8_t *>(returnData), bufferSize);
6210                 std::shared_ptr<Media::PixelMap> pixelMapToJs(pixelMap.release());
6211                 jsPixelMap = OHOS::Media::PixelMapNapi::CreatePixelMap(env, pixelMapToJs);
6212             } else {
6213                 WVLOG_E("WebPageSnapshot create pixel map error");
6214             }
6215             napi_set_named_property(env, jsResult, "imagePixelMap", jsPixelMap);
6216 
6217             int returnJsWidth = 0;
6218             int returnJsHeight = 0;
6219             if (radio > 0) {
6220                 returnJsWidth = returnWidth / radio;
6221                 returnJsHeight = returnHeight / radio;
6222             }
6223             if (check) {
6224                 if (std::abs(returnJsWidth - inputWidth) < INTEGER_THREE) {
6225                     returnJsWidth = inputWidth;
6226                 }
6227 
6228                 if (std::abs(returnJsHeight - inputHeight) < INTEGER_THREE) {
6229                     returnJsHeight = inputHeight;
6230                 }
6231             }
6232             napi_value jsSizeObj = nullptr;
6233             napi_create_object(env, &jsSizeObj);
6234             napi_value jsSize[2] = {0};
6235             napi_create_int32(env, returnJsWidth, &jsSize[0]);
6236             napi_create_int32(env, returnJsHeight, &jsSize[1]);
6237             napi_set_named_property(env, jsSizeObj, "width", jsSize[0]);
6238             napi_set_named_property(env, jsSizeObj, "height", jsSize[1]);
6239             napi_set_named_property(env, jsResult, "size", jsSizeObj);
6240 
6241             napi_value jsId = nullptr;
6242             napi_create_string_utf8(env, returnId, strlen(returnId), &jsId);
6243             napi_set_named_property(env, jsResult, "id", jsId);
6244 
6245             napi_value jsStatus = nullptr;
6246             napi_get_boolean(env, returnStatus, &jsStatus);
6247             napi_set_named_property(env, jsResult, "status", jsStatus);
6248 
6249             napi_value jsError = nullptr;
6250             napi_get_undefined(env, &jsError);
6251             napi_value args[INTEGER_TWO] = {jsError, jsResult};
6252 
6253             napi_value callback = nullptr;
6254             napi_value callbackResult = nullptr;
6255             napi_get_reference_value(env, jCallback, &callback);
6256 
6257             napi_call_function(env, nullptr, callback, INTEGER_TWO, args, &callbackResult);
6258             napi_delete_reference(env, jCallback);
6259             g_inWebPageSnapshot = false;
6260         };
6261 }
6262 
WebPageSnapshot(napi_env env, napi_callback_info info)6263 napi_value NapiWebviewController::WebPageSnapshot(napi_env env, napi_callback_info info)
6264 {
6265     napi_value thisVar = nullptr;
6266     napi_value result = nullptr;
6267     size_t argc = INTEGER_TWO;
6268     napi_value argv[INTEGER_TWO] = {0};
6269 
6270     napi_get_undefined(env, &result);
6271     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
6272 
6273     if (argc != INTEGER_TWO) {
6274         WVLOG_E("WebPageSnapshot: args count is not allowed.");
6275         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
6276         return result;
6277     }
6278 
6279     napi_ref callback = nullptr;
6280     napi_create_reference(env, argv[INTEGER_ONE], INTEGER_ONE, &callback);
6281     if (!callback) {
6282         WVLOG_E("WebPageSnapshot failed to create reference for callback");
6283         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR);
6284         return result;
6285     }
6286 
6287     WebviewController *webviewController = GetWebviewController(env, info);
6288     if (!webviewController) {
6289         WVLOG_E("WebPageSnapshot init webview controller error.");
6290         napi_delete_reference(env, callback);
6291         return result;
6292     }
6293 
6294     if (g_inWebPageSnapshot) {
6295         JsErrorCallback(env, std::move(callback), FUNCTION_NOT_ENABLE);
6296         napi_delete_reference(env, callback);
6297         return result;
6298     }
6299     g_inWebPageSnapshot = true;
6300 
6301     napi_value snapshotId = nullptr;
6302     napi_value snapshotSize = nullptr;
6303     napi_value snapshotSizeWidth = nullptr;
6304     napi_value snapshotSizeHeight = nullptr;
6305 
6306     std::string nativeSnapshotId = "";
6307     int32_t nativeSnapshotSizeWidth = 0;
6308     int32_t nativeSnapshotSizeHeight = 0;
6309     PixelUnit nativeSnapshotSizeWidthType = PixelUnit::NONE;
6310     PixelUnit nativeSnapshotSizeHeightType = PixelUnit::NONE;
6311     PixelUnit nativeSnapshotSizeType = PixelUnit::NONE;
6312 
6313     if (napi_get_named_property(env, argv[INTEGER_ZERO], "id", &snapshotId) == napi_ok) {
6314         NapiParseUtils::ParseString(env, snapshotId, nativeSnapshotId);
6315     }
6316 
6317     if (napi_get_named_property(env, argv[INTEGER_ZERO], "size", &snapshotSize) == napi_ok) {
6318         if (napi_get_named_property(env, snapshotSize, "width", &snapshotSizeWidth) == napi_ok) {
6319             if (!webviewController->ParseJsLengthToInt(env, snapshotSizeWidth,
6320                                                        nativeSnapshotSizeWidthType,
6321                                                        nativeSnapshotSizeWidth)) {
6322                 JsErrorCallback(env, std::move(callback), PARAM_CHECK_ERROR);
6323                 g_inWebPageSnapshot = false;
6324                 napi_delete_reference(env, callback);
6325                 return result;
6326             }
6327         }
6328         if (napi_get_named_property(env, snapshotSize, "height", &snapshotSizeHeight) == napi_ok) {
6329             if (!webviewController->ParseJsLengthToInt(env, snapshotSizeHeight,
6330                                                        nativeSnapshotSizeHeightType,
6331                                                        nativeSnapshotSizeHeight)) {
6332                 JsErrorCallback(env, std::move(callback), PARAM_CHECK_ERROR);
6333                 g_inWebPageSnapshot = false;
6334                 napi_delete_reference(env, callback);
6335                 return result;
6336             }
6337         }
6338     }
6339 
6340     if (nativeSnapshotSizeWidthType != PixelUnit::NONE && nativeSnapshotSizeHeightType != PixelUnit::NONE &&
6341         nativeSnapshotSizeWidthType != nativeSnapshotSizeHeightType) {
6342         WVLOG_E("WebPageSnapshot input different pixel unit");
6343         JsErrorCallback(env, std::move(callback), PARAM_CHECK_ERROR);
6344         g_inWebPageSnapshot = false;
6345         napi_delete_reference(env, callback);
6346         return result;
6347     }
6348 
6349     if (nativeSnapshotSizeWidthType != PixelUnit::NONE) {
6350         nativeSnapshotSizeType = nativeSnapshotSizeWidthType;
6351     }
6352     if (nativeSnapshotSizeHeightType != PixelUnit::NONE) {
6353         nativeSnapshotSizeType = nativeSnapshotSizeHeightType;
6354     }
6355     if (nativeSnapshotSizeWidth < 0 || nativeSnapshotSizeHeight < 0) {
6356         WVLOG_E("WebPageSnapshot input pixel length less than 0");
6357         JsErrorCallback(env, std::move(callback), PARAM_CHECK_ERROR);
6358         g_inWebPageSnapshot = false;
6359         napi_delete_reference(env, callback);
6360         return result;
6361     }
6362     bool pixelCheck = false;
6363     if (nativeSnapshotSizeType == PixelUnit::VP) {
6364         pixelCheck = true;
6365     }
6366     WVLOG_I("WebPageSnapshot pixel type :%{public}d", static_cast<int>(nativeSnapshotSizeType));
6367 
6368     auto resultCallback = CreateWebPageSnapshotResultCallback(
6369         env, std::move(callback), pixelCheck, nativeSnapshotSizeWidth, nativeSnapshotSizeHeight);
6370 
6371     ErrCode ret = webviewController->WebPageSnapshot(nativeSnapshotId.c_str(),
6372         nativeSnapshotSizeType,
6373         nativeSnapshotSizeWidth,
6374         nativeSnapshotSizeHeight,
6375         std::move(resultCallback));
6376     if (ret != NO_ERROR) {
6377         g_inWebPageSnapshot = false;
6378         BusinessError::ThrowErrorByErrcode(env, ret);
6379     }
6380     return result;
6381 }
6382 
SetPathAllowingUniversalAccess( napi_env env, napi_callback_info info)6383 napi_value NapiWebviewController::SetPathAllowingUniversalAccess(
6384     napi_env env, napi_callback_info info)
6385 {
6386     napi_value result = nullptr;
6387     napi_value thisVar = nullptr;
6388     size_t argc = INTEGER_ONE;
6389     napi_value argv[INTEGER_ONE] = { 0 };
6390     NAPI_CALL(env, napi_get_undefined(env, &result));
6391     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
6392     WebviewController *webviewController = GetWebviewController(env, info);
6393     if (!webviewController) {
6394         WVLOG_E("SetPathAllowingUniversalAccess init webview controller error.");
6395         return result;
6396     }
6397     bool isArray = false;
6398     NAPI_CALL(env, napi_is_array(env, argv[INTEGER_ZERO], &isArray));
6399     if (!isArray) {
6400         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6401             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "pathList", "Array<string>"));
6402         return result;
6403     }
6404     std::vector<std::string> pathList;
6405     uint32_t pathCount = 0;
6406     NAPI_CALL(env, napi_get_array_length(env, argv[INTEGER_ZERO], &pathCount));
6407     for (uint32_t i = 0 ; i < pathCount ; i++) {
6408         napi_value pathItem = nullptr;
6409         napi_get_element(env, argv[INTEGER_ZERO], i, &pathItem);
6410         std::string path;
6411         if (!NapiParseUtils::ParseString(env, pathItem, path)) {
6412             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6413                 NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "pathList", "Array<string>"));
6414             return result;
6415         }
6416         if (path.empty()) {
6417             BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6418                 NWebError::FormatString("BusinessError 401: Parameter error. Path: '%s' is invalid", path.c_str()));
6419             return result;
6420         }
6421         pathList.emplace_back(path);
6422     }
6423     std::string errorPath;
6424     webviewController->SetPathAllowingUniversalAccess(pathList, errorPath);
6425     if (!errorPath.empty()) {
6426         WVLOG_E("%{public}s is invalid.", errorPath.c_str());
6427         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6428             NWebError::FormatString("BusinessError 401: Parameter error. Path: '%s' is invalid", errorPath.c_str()));
6429     }
6430     return result;
6431 }
6432 
TrimMemoryByPressureLevel(napi_env env, napi_callback_info info)6433 napi_value NapiWebviewController::TrimMemoryByPressureLevel(napi_env env,
6434     napi_callback_info info)
6435 {
6436     napi_value thisVar = nullptr;
6437     napi_value result = nullptr;
6438     size_t argc = INTEGER_ONE;
6439     napi_value argv[INTEGER_ONE] = { 0 };
6440     int32_t memoryLevel;
6441     napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
6442     if (argc != INTEGER_ONE) {
6443         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6444             NWebError::FormatString(
6445                 ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "one"));
6446         return result;
6447     }
6448 
6449     if (!NapiParseUtils::ParseInt32(env, argv[INTEGER_ZERO], memoryLevel)) {
6450         BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6451             NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR,
6452                                     "PressureLevel", "number"));
6453         return result;
6454     }
6455 
6456     memoryLevel = memoryLevel == 1 ? 0 : memoryLevel;
6457     NWebHelper::Instance().TrimMemoryByPressureLevel(memoryLevel);
6458     NAPI_CALL(env, napi_get_undefined(env, &result));
6459     return result;
6460 }
6461 
GetScrollOffset(napi_env env, napi_callback_info info)6462 napi_value NapiWebviewController::GetScrollOffset(napi_env env,
6463     napi_callback_info info)
6464 {
6465     napi_value result = nullptr;
6466     napi_value horizontal;
6467     napi_value vertical;
6468     float offsetX = 0;
6469     float offsetY = 0;
6470 
6471     WebviewController* webviewController = GetWebviewController(env, info);
6472     if (!webviewController) {
6473         return nullptr;
6474     }
6475 
6476     webviewController->GetScrollOffset(&offsetX, &offsetY);
6477 
6478     napi_create_object(env, &result);
6479     napi_create_double(env, static_cast<double>(offsetX), &horizontal);
6480     napi_create_double(env, static_cast<double>(offsetY), &vertical);
6481     napi_set_named_property(env, result, "x", horizontal);
6482     napi_set_named_property(env, result, "y", vertical);
6483     return result;
6484 }
6485 
ScrollByWithResult(napi_env env, napi_callback_info info)6486 napi_value NapiWebviewController::ScrollByWithResult(napi_env env, napi_callback_info info)
6487 {
6488    napi_value thisVar = nullptr;
6489    napi_value result = nullptr;
6490    size_t argc = INTEGER_TWO;
6491    napi_value argv[INTEGER_TWO] = { 0 };
6492    float deltaX;
6493    float deltaY;
6494 
6495    napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr);
6496    if (argc != INTEGER_TWO) {
6497        BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6498            NWebError::FormatString(ParamCheckErrorMsgTemplate::PARAM_NUMBERS_ERROR_ONE, "two"));
6499        return result;
6500    }
6501 
6502    if (!NapiParseUtils::ParseFloat(env, argv[INTEGER_ZERO], deltaX)) {
6503        BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6504            NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "deltaX", "number"));
6505        return result;
6506    }
6507 
6508    if (!NapiParseUtils::ParseFloat(env, argv[INTEGER_ONE], deltaY)) {
6509        BusinessError::ThrowErrorByErrcode(env, PARAM_CHECK_ERROR,
6510            NWebError::FormatString(ParamCheckErrorMsgTemplate::TYPE_ERROR, "deltaY", "number"));
6511        return result;
6512    }
6513 
6514    WebviewController *webviewController = GetWebviewController(env, info);
6515    if (!webviewController) {
6516        return nullptr;
6517    }
6518 
6519    bool scrollByWithResult = webviewController->ScrollByWithResult(deltaX, deltaY);
6520    NAPI_CALL(env, napi_get_boolean(env, scrollByWithResult, &result));
6521    return result;
6522 }
6523 } // namespace NWeb
6524 } // namespace OHOS
6525