1 /*
2 * Copyright (c) 2022-2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include <unordered_map>
17
18 #include "installer.h"
19
20 #include "appexecfwk_errors.h"
21 #include "app_log_wrapper.h"
22 #include "bundle_errors.h"
23 #include "bundle_death_recipient.h"
24 #include "bundle_mgr_interface.h"
25 #include "bundle_mgr_proxy.h"
26 #include "business_error.h"
27 #include "common_func.h"
28 #include "if_system_ability_manager.h"
29 #include "installer_callback.h"
30 #include "napi_arg.h"
31 #include "napi_constants.h"
32 #include "system_ability_definition.h"
33 #include "ipc_skeleton.h"
34
35 namespace OHOS {
36 namespace AppExecFwk {
37 namespace {
38 // resource name
39 const char* RESOURCE_NAME_OF_GET_BUNDLE_INSTALLER = "GetBundleInstaller";
40 const char* RESOURCE_NAME_OF_GET_BUNDLE_INSTALLER_SYNC = "GetBundleInstallerSync";
41 const char* RESOURCE_NAME_OF_INSTALL = "Install";
42 const char* RESOURCE_NAME_OF_UNINSTALL = "Uninstall";
43 const char* RESOURCE_NAME_OF_RECOVER = "Recover";
44 const char* RESOURCE_NAME_OF_UPDATE_BUNDLE_FOR_SELF = "UpdateBundleForSelf";
45 const char* RESOURCE_NAME_OF_UNINSTALL_AND_RECOVER = "UninstallAndRecover";
46 const char* EMPTY_STRING = "";
47 // install message
48 constexpr const char* INSTALL_PERMISSION =
49 "ohos.permission.INSTALL_BUNDLE or "
50 "ohos.permission.INSTALL_ENTERPRISE_BUNDLE or "
51 "ohos.permission.INSTALL_ENTERPRISE_MDM_BUNDLE or "
52 "ohos.permission.INSTALL_ENTERPRISE_NORMAL_BUNDLE or "
53 "ohos.permission.INSTALL_INTERNALTESTING_BUNDLE";
54 constexpr const char* UNINSTALL_PERMISSION = "ohos.permission.INSTALL_BUNDLE or ohos.permission.UNINSTALL_BUNDLE";
55 constexpr const char* RECOVER_PERMISSION = "ohos.permission.INSTALL_BUNDLE or ohos.permission.RECOVER_BUNDLE";
56 constexpr const char* INSTALL_SELF_PERMISSION = "ohos.permission.INSTALL_SELF_BUNDLE";
57 constexpr const char* PARAMETERS = "parameters";
58 constexpr const char* CORRESPONDING_TYPE = "corresponding type";
59 constexpr const char* FUNCTION_TYPE = "napi_function";
60 constexpr const char* CALLBACK = "callback";
61 // property name
62 const char* USER_ID = "userId";
63 const char* INSTALL_FLAG = "installFlag";
64 const char* IS_KEEP_DATA = "isKeepData";
65 const char* CROWD_TEST_DEADLINE = "crowdtestDeadline";
66 const char* MODULE_NAME = "moduleName";
67 const char* HASH_VALUE = "hashValue";
68 const char* HASH_PARAMS = "hashParams";
69 const char* BUNDLE_NAME = "bundleName";
70 const char* APP_INDEX = "appIndex";
71 const char* FILE_PATH = "filePath";
72 const char* ADD_EXT_RESOURCE = "AddExtResource";
73 const char* REMOVE_EXT_RESOURCE = "RemoveExtResource";
74 const char* VERSION_CODE = "versionCode";
75 const char* SHARED_BUNDLE_DIR_PATHS = "sharedBundleDirPaths";
76 const char* SPECIFIED_DISTRIBUTION_TYPE = "specifiedDistributionType";
77 const char* ADDITIONAL_INFO = "additionalInfo";
78 const char* VERIFY_CODE_PARAM = "verifyCodeParams";
79 const char* SIGNATURE_FILE_PATH = "signatureFilePath";
80 const char* PGO_PARAM = "pgoParams";
81 const char* PGO_FILE_PATH = "pgoFilePath";
82 const char* HAPS_FILE_NEEDED =
83 "BusinessError 401: Parameter error. parameter hapFiles is needed for code signature";
84 const char* CREATE_APP_CLONE = "CreateAppClone";
85 const char* DESTROY_APP_CLONE = "destroyAppClone";
86 const char* INSTALL_PREEXISTING_APP = "installPreexistingApp";
87 constexpr int32_t FIRST_PARAM = 0;
88 constexpr int32_t SECOND_PARAM = 1;
89
90 constexpr int32_t SPECIFIED_DISTRIBUTION_TYPE_MAX_SIZE = 128;
91 constexpr int32_t ADDITIONAL_INFO_MAX_SIZE = 3000;
92 constexpr int32_t ILLEGAL_APP_INDEX = -1;
93 } // namespace
94 napi_ref thread_local g_classBundleInstaller;
95 bool g_isSystemApp = false;
96
~AsyncInstallCallbackInfo()97 AsyncInstallCallbackInfo::~AsyncInstallCallbackInfo()
98 {
99 if (callback) {
100 napi_delete_reference(env, callback);
101 callback = nullptr;
102 }
103 if (asyncWork) {
104 napi_delete_async_work(env, asyncWork);
105 asyncWork = nullptr;
106 }
107 }
108
~AsyncGetBundleInstallerCallbackInfo()109 AsyncGetBundleInstallerCallbackInfo::~AsyncGetBundleInstallerCallbackInfo()
110 {
111 if (callback) {
112 napi_delete_reference(env, callback);
113 callback = nullptr;
114 }
115 if (asyncWork) {
116 napi_delete_async_work(env, asyncWork);
117 asyncWork = nullptr;
118 }
119 }
120
GetBundleInstallerCompleted(napi_env env, napi_status status, void *data)121 void GetBundleInstallerCompleted(napi_env env, napi_status status, void *data)
122 {
123 AsyncGetBundleInstallerCallbackInfo *asyncCallbackInfo =
124 reinterpret_cast<AsyncGetBundleInstallerCallbackInfo *>(data);
125 std::unique_ptr<AsyncGetBundleInstallerCallbackInfo> callbackPtr {asyncCallbackInfo};
126
127 napi_value m_classBundleInstaller = nullptr;
128 NAPI_CALL_RETURN_VOID(env, napi_get_reference_value(env, g_classBundleInstaller,
129 &m_classBundleInstaller));
130 napi_value result[CALLBACK_PARAM_SIZE] = {0};
131 auto iBundleMgr = CommonFunc::GetBundleMgr();
132 if (iBundleMgr == nullptr) {
133 APP_LOGE("can not get iBundleMgr");
134 return;
135 }
136 if (!g_isSystemApp && !iBundleMgr->VerifySystemApi(Constants::INVALID_API_VERSION)) {
137 APP_LOGE("non-system app calling system api");
138 result[0] = BusinessError::CreateCommonError(
139 env, ERROR_NOT_SYSTEM_APP, RESOURCE_NAME_OF_GET_BUNDLE_INSTALLER, INSTALL_PERMISSION);
140 if (callbackPtr->deferred) {
141 NAPI_CALL_RETURN_VOID(env, napi_reject_deferred(env, asyncCallbackInfo->deferred, result[0]));
142 } else {
143 napi_value callback = nullptr;
144 napi_value placeHolder = nullptr;
145 NAPI_CALL_RETURN_VOID(env, napi_get_reference_value(env, asyncCallbackInfo->callback, &callback));
146 NAPI_CALL_RETURN_VOID(env, napi_call_function(env, nullptr, callback,
147 sizeof(result) / sizeof(result[0]), result, &placeHolder));
148 }
149 return;
150 }
151 g_isSystemApp = true;
152 NAPI_CALL_RETURN_VOID(env, napi_new_instance(env, m_classBundleInstaller, 0, nullptr, &result[SECOND_PARAM]));
153
154 if (callbackPtr->deferred) {
155 NAPI_CALL_RETURN_VOID(env, napi_resolve_deferred(env, callbackPtr->deferred, result[SECOND_PARAM]));
156 } else {
157 napi_value callback = CommonFunc::WrapVoidToJS(env);
158 NAPI_CALL_RETURN_VOID(env, napi_get_reference_value(env, callbackPtr->callback, &callback));
159 napi_value undefined = CommonFunc::WrapVoidToJS(env);
160 NAPI_CALL_RETURN_VOID(env, napi_get_undefined(env, &undefined));
161 napi_value callResult = CommonFunc::WrapVoidToJS(env);
162 NAPI_CALL_RETURN_VOID(env, napi_call_function(env, undefined, callback, CALLBACK_PARAM_SIZE,
163 &result[FIRST_PARAM], &callResult));
164 }
165 }
166
167 /**
168 * Promise and async callback
169 */
GetBundleInstaller(napi_env env, napi_callback_info info)170 napi_value GetBundleInstaller(napi_env env, napi_callback_info info)
171 {
172 APP_LOGI_NOFUNC("napi GetBundleInstaller called");
173 NapiArg args(env, info);
174 if (!args.Init(FIRST_PARAM, SECOND_PARAM)) {
175 APP_LOGE("GetBundleInstaller args init failed");
176 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
177 return nullptr;
178 }
179 std::unique_ptr<AsyncGetBundleInstallerCallbackInfo> callbackPtr =
180 std::make_unique<AsyncGetBundleInstallerCallbackInfo>(env);
181
182 auto argc = args.GetMaxArgc();
183 APP_LOGD("GetBundleInstaller argc = [%{public}zu]", argc);
184 // check param
185 if (argc == SECOND_PARAM) {
186 napi_value arg = args.GetArgv(argc - SECOND_PARAM);
187 if (arg == nullptr) {
188 APP_LOGE("the param is nullptr");
189 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
190 return nullptr;
191 }
192 napi_valuetype valuetype = napi_undefined;
193 NAPI_CALL(env, napi_typeof(env, arg, &valuetype));
194 if (valuetype != napi_function) {
195 APP_LOGE("the param type is invalid");
196 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, CALLBACK, FUNCTION_TYPE);
197 return nullptr;
198 }
199 NAPI_CALL(env, napi_create_reference(env, arg, NAPI_RETURN_ONE, &callbackPtr->callback));
200 }
201
202 auto executeFunc = [](napi_env env, void *data) {};
203 napi_value promise = CommonFunc::AsyncCallNativeMethod(
204 env,
205 callbackPtr.get(),
206 RESOURCE_NAME_OF_GET_BUNDLE_INSTALLER,
207 executeFunc,
208 GetBundleInstallerCompleted);
209 callbackPtr.release();
210 APP_LOGI_NOFUNC("call GetBundleInstaller done");
211 return promise;
212 }
213
GetBundleInstallerSync(napi_env env, napi_callback_info info)214 napi_value GetBundleInstallerSync(napi_env env, napi_callback_info info)
215 {
216 APP_LOGI("NAPI GetBundleInstallerSync called");
217 napi_value m_classBundleInstaller = nullptr;
218 NAPI_CALL(env, napi_get_reference_value(env, g_classBundleInstaller,
219 &m_classBundleInstaller));
220 auto iBundleMgr = CommonFunc::GetBundleMgr();
221 if (iBundleMgr == nullptr) {
222 APP_LOGE("can not get iBundleMgr");
223 return nullptr;
224 }
225 if (!g_isSystemApp && !iBundleMgr->VerifySystemApi(Constants::INVALID_API_VERSION)) {
226 APP_LOGE("non-system app calling system api");
227 napi_value businessError = BusinessError::CreateCommonError(
228 env, ERROR_NOT_SYSTEM_APP, RESOURCE_NAME_OF_GET_BUNDLE_INSTALLER_SYNC, INSTALL_PERMISSION);
229 napi_throw(env, businessError);
230 return nullptr;
231 }
232 g_isSystemApp = true;
233 napi_value nBundleInstaller = nullptr;
234 NAPI_CALL(env, napi_new_instance(env, m_classBundleInstaller, 0, nullptr, &nBundleInstaller));
235 APP_LOGD("call GetBundleInstallerSync done");
236 return nBundleInstaller;
237 APP_LOGI("call GetBundleInstallerSync done");
238 }
239
CreateErrCodeMap(std::unordered_map<int32_t, int32_t> &errCodeMap)240 static void CreateErrCodeMap(std::unordered_map<int32_t, int32_t> &errCodeMap)
241 {
242 errCodeMap = {
243 { IStatusReceiver::SUCCESS, SUCCESS},
244 { IStatusReceiver::ERR_INSTALL_INTERNAL_ERROR, ERROR_BUNDLE_SERVICE_EXCEPTION },
245 { IStatusReceiver::ERR_INSTALL_HOST_INSTALLER_FAILED, ERROR_BUNDLE_SERVICE_EXCEPTION },
246 { IStatusReceiver::ERR_INSTALLD_PARAM_ERROR, ERROR_BUNDLE_SERVICE_EXCEPTION },
247 { IStatusReceiver::ERR_INSTALLD_GET_PROXY_ERROR, ERROR_BUNDLE_SERVICE_EXCEPTION },
248 { IStatusReceiver::ERR_INSTALL_INSTALLD_SERVICE_ERROR, ERROR_BUNDLE_SERVICE_EXCEPTION },
249 { IStatusReceiver::ERR_UNINSTALL_BUNDLE_MGR_SERVICE_ERROR, ERROR_BUNDLE_SERVICE_EXCEPTION },
250 { IStatusReceiver::ERR_FAILED_SERVICE_DIED, ERROR_BUNDLE_SERVICE_EXCEPTION },
251 { IStatusReceiver::ERR_FAILED_GET_INSTALLER_PROXY, ERROR_BUNDLE_SERVICE_EXCEPTION },
252 { IStatusReceiver::ERR_USER_CREATE_FAILED, ERROR_BUNDLE_SERVICE_EXCEPTION },
253 { IStatusReceiver::ERR_USER_REMOVE_FAILED, ERROR_BUNDLE_SERVICE_EXCEPTION },
254 { IStatusReceiver::ERR_UNINSTALL_KILLING_APP_ERROR, ERROR_BUNDLE_SERVICE_EXCEPTION },
255 { IStatusReceiver::ERR_INSTALL_GENERATE_UID_ERROR, ERROR_BUNDLE_SERVICE_EXCEPTION },
256 { IStatusReceiver::ERR_INSTALL_STATE_ERROR, ERROR_BUNDLE_SERVICE_EXCEPTION },
257 { IStatusReceiver::ERR_RECOVER_NOT_ALLOWED, ERROR_BUNDLE_SERVICE_EXCEPTION },
258 { IStatusReceiver::ERR_RECOVER_GET_BUNDLEPATH_ERROR, ERROR_BUNDLE_SERVICE_EXCEPTION },
259 { IStatusReceiver::ERR_UNINSTALL_AND_RECOVER_NOT_PREINSTALLED_BUNDLE, ERROR_BUNDLE_NOT_PREINSTALLED },
260 { IStatusReceiver::ERR_UNINSTALL_SYSTEM_APP_ERROR, ERROR_UNINSTALL_PREINSTALL_APP_FAILED },
261 { IStatusReceiver::ERR_INSTALL_PARSE_FAILED, ERROR_INSTALL_PARSE_FAILED },
262 { IStatusReceiver::ERR_INSTALL_PARSE_UNEXPECTED, ERROR_INSTALL_PARSE_FAILED },
263 { IStatusReceiver::ERR_INSTALL_PARSE_MISSING_BUNDLE, ERROR_INSTALL_PARSE_FAILED },
264 { IStatusReceiver::ERR_INSTALL_PARSE_NO_PROFILE, ERROR_INSTALL_PARSE_FAILED },
265 { IStatusReceiver::ERR_INSTALL_PARSE_BAD_PROFILE, ERROR_INSTALL_PARSE_FAILED },
266 { IStatusReceiver::ERR_INSTALL_PARSE_PROFILE_PROP_TYPE_ERROR, ERROR_INSTALL_PARSE_FAILED },
267 { IStatusReceiver::ERR_INSTALL_PARSE_PROFILE_MISSING_PROP, ERROR_INSTALL_PARSE_FAILED },
268 { IStatusReceiver::ERR_INSTALL_PARSE_PERMISSION_ERROR, ERROR_INSTALL_PARSE_FAILED },
269 { IStatusReceiver::ERR_INSTALL_PARSE_PROFILE_PROP_CHECK_ERROR, ERROR_INSTALL_PARSE_FAILED },
270 { IStatusReceiver::ERR_INSTALL_PARSE_RPCID_FAILED, ERROR_INSTALL_PARSE_FAILED },
271 { IStatusReceiver::ERR_INSTALL_PARSE_NATIVE_SO_FAILED, ERROR_INSTALL_PARSE_FAILED },
272 { IStatusReceiver::ERR_INSTALL_PARSE_AN_FAILED, ERROR_INSTALL_PARSE_FAILED },
273 { IStatusReceiver::ERR_INSTALL_PARSE_MISSING_ABILITY, ERROR_INSTALL_PARSE_FAILED },
274 { IStatusReceiver::ERR_INSTALL_FAILED_PROFILE_PARSE_FAIL, ERROR_INSTALL_PARSE_FAILED },
275 { IStatusReceiver::ERR_INSTALL_VERIFICATION_FAILED, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
276 { IStatusReceiver::ERR_INSTALL_FAILED_INCOMPATIBLE_SIGNATURE, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
277 { IStatusReceiver::ERR_INSTALL_FAILED_INVALID_SIGNATURE_FILE_PATH, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
278 { IStatusReceiver::ERR_INSTALL_FAILED_BAD_BUNDLE_SIGNATURE_FILE, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
279 { IStatusReceiver::ERR_INSTALL_FAILED_NO_BUNDLE_SIGNATURE, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
280 { IStatusReceiver::ERR_INSTALL_FAILED_VERIFY_APP_PKCS7_FAIL, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
281 { IStatusReceiver::ERR_INSTALL_FAILED_APP_SOURCE_NOT_TRUESTED, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
282 { IStatusReceiver::ERR_INSTALL_FAILED_BAD_DIGEST, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
283 { IStatusReceiver::ERR_INSTALL_FAILED_BUNDLE_INTEGRITY_VERIFICATION_FAILURE,
284 ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
285 { IStatusReceiver::ERR_INSTALL_FAILED_BAD_PUBLICKEY, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
286 { IStatusReceiver::ERR_INSTALL_FAILED_BAD_BUNDLE_SIGNATURE, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
287 { IStatusReceiver::ERR_INSTALL_FAILED_NO_PROFILE_BLOCK_FAIL, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
288 { IStatusReceiver::ERR_INSTALL_FAILED_BUNDLE_SIGNATURE_VERIFICATION_FAILURE,
289 ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
290 { IStatusReceiver::ERR_INSTALL_FAILED_VERIFY_SOURCE_INIT_FAIL, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
291 { IStatusReceiver::ERR_INSTALL_SINGLETON_INCOMPATIBLE, ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
292 { IStatusReceiver::ERR_INSTALL_FAILED_INCONSISTENT_SIGNATURE, ERROR_INSTALL_FAILED_INCONSISTENT_SIGNATURE },
293 { IStatusReceiver::ERR_INSTALL_PARAM_ERROR, ERROR_BUNDLE_NOT_EXIST },
294 { IStatusReceiver::ERR_UNINSTALL_PARAM_ERROR, ERROR_BUNDLE_NOT_EXIST },
295 { IStatusReceiver::ERR_RECOVER_INVALID_BUNDLE_NAME, ERROR_BUNDLE_NOT_EXIST },
296 { IStatusReceiver::ERR_UNINSTALL_INVALID_NAME, ERROR_BUNDLE_NOT_EXIST },
297 { IStatusReceiver::ERR_INSTALL_INVALID_BUNDLE_FILE, ERROR_INSTALL_HAP_FILEPATH_INVALID },
298 { IStatusReceiver::ERR_INSTALL_FAILED_MODULE_NAME_EMPTY, ERROR_MODULE_NOT_EXIST },
299 { IStatusReceiver::ERR_INSTALL_FAILED_MODULE_NAME_DUPLICATE, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
300 { IStatusReceiver::ERR_INSTALL_FAILED_CHECK_HAP_HASH_PARAM, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
301 { IStatusReceiver::ERR_UNINSTALL_MISSING_INSTALLED_BUNDLE, ERROR_BUNDLE_NOT_EXIST },
302 { IStatusReceiver::ERR_UNINSTALL_MISSING_INSTALLED_MODULE, ERROR_MODULE_NOT_EXIST },
303 { IStatusReceiver::ERR_USER_NOT_INSTALL_HAP, ERROR_BUNDLE_NOT_EXIST },
304 { IStatusReceiver::ERR_INSTALL_FILE_PATH_INVALID, ERROR_INSTALL_HAP_FILEPATH_INVALID },
305 { IStatusReceiver::ERR_INSTALL_PERMISSION_DENIED, ERROR_PERMISSION_DENIED_ERROR },
306 { IStatusReceiver::ERR_UNINSTALL_PERMISSION_DENIED, ERROR_PERMISSION_DENIED_ERROR },
307 { IStatusReceiver::ERR_INSTALL_GRANT_REQUEST_PERMISSIONS_FAILED, ERROR_INSTALL_PERMISSION_CHECK_ERROR },
308 { IStatusReceiver::ERR_INSTALL_UPDATE_HAP_TOKEN_FAILED, ERROR_INSTALL_PERMISSION_CHECK_ERROR },
309 { IStatusReceiver::ERR_INSTALLD_CREATE_DIR_FAILED, ERROR_BUNDLE_SERVICE_EXCEPTION },
310 { IStatusReceiver::ERR_INSTALLD_CHOWN_FAILED, ERROR_BUNDLE_SERVICE_EXCEPTION },
311 { IStatusReceiver::ERR_INSTALLD_CREATE_DIR_EXIST, ERROR_BUNDLE_SERVICE_EXCEPTION },
312 { IStatusReceiver::ERR_INSTALLD_REMOVE_DIR_FAILED, ERROR_BUNDLE_SERVICE_EXCEPTION },
313 { IStatusReceiver::ERR_INSTALLD_EXTRACT_FILES_FAILED, ERROR_BUNDLE_SERVICE_EXCEPTION },
314 { IStatusReceiver::ERR_INSTALLD_RNAME_DIR_FAILED, ERROR_BUNDLE_SERVICE_EXCEPTION },
315 { IStatusReceiver::ERR_INSTALLD_CLEAN_DIR_FAILED, ERROR_BUNDLE_SERVICE_EXCEPTION },
316 { IStatusReceiver::ERR_INSTALL_ENTRY_ALREADY_EXIST, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
317 { IStatusReceiver::ERR_INSTALL_ALREADY_EXIST, ERROR_INSTALL_ALREADY_EXIST },
318 { IStatusReceiver::ERR_INSTALL_BUNDLENAME_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
319 { IStatusReceiver::ERR_INSTALL_VERSIONCODE_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
320 { IStatusReceiver::ERR_INSTALL_VERSIONNAME_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
321 { IStatusReceiver::ERR_INSTALL_MINCOMPATIBLE_VERSIONCODE_NOT_SAME,
322 ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
323 { IStatusReceiver::ERR_INSTALL_VENDOR_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
324 { IStatusReceiver::ERR_INSTALL_RELEASETYPE_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
325 { IStatusReceiver::ERR_INSTALL_RELEASETYPE_TARGET_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
326 { IStatusReceiver::ERR_INSTALL_RELEASETYPE_COMPATIBLE_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
327 { IStatusReceiver::ERR_INSTALL_SINGLETON_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
328 { IStatusReceiver::ERR_INSTALL_ZERO_USER_WITH_NO_SINGLETON, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
329 { IStatusReceiver::ERR_INSTALL_CHECK_SYSCAP_FAILED, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
330 { IStatusReceiver::ERR_INSTALL_APPTYPE_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
331 { IStatusReceiver::ERR_INSTALL_URI_DUPLICATE, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
332 { IStatusReceiver::ERR_INSTALL_VERSION_NOT_COMPATIBLE, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
333 { IStatusReceiver::ERR_INSTALL_APP_DISTRIBUTION_TYPE_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
334 { IStatusReceiver::ERR_INSTALL_APP_PROVISION_TYPE_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
335 { IStatusReceiver::ERR_INSTALL_SO_INCOMPATIBLE, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
336 { IStatusReceiver::ERR_INSTALL_AN_INCOMPATIBLE, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
337 { IStatusReceiver::ERR_INSTALL_TYPE_ERROR, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
338 { IStatusReceiver::ERR_INSTALL_TYPE_ERROR, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
339 { IStatusReceiver::ERR_INSTALL_NOT_UNIQUE_DISTRO_MODULE_NAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
340 { IStatusReceiver::ERR_INSTALL_INCONSISTENT_MODULE_NAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
341 { IStatusReceiver::ERR_INSTALL_INVALID_NUMBER_OF_ENTRY_HAP, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
342 { IStatusReceiver::ERR_INSTALL_ASAN_ENABLED_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
343 { IStatusReceiver::ERR_INSTALL_ASAN_ENABLED_NOT_SUPPORT, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT},
344 { IStatusReceiver::ERR_INSTALL_BUNDLE_TYPE_NOT_SAME, ERROR_INSTALL_PARSE_FAILED},
345 { IStatusReceiver::ERR_INSTALL_DISK_MEM_INSUFFICIENT, ERROR_INSTALL_NO_DISK_SPACE_LEFT },
346 { IStatusReceiver::ERR_USER_NOT_EXIST, ERROR_INVALID_USER_ID },
347 { IStatusReceiver::ERR_INSTALL_VERSION_DOWNGRADE, ERROR_INSTALL_VERSION_DOWNGRADE },
348 { IStatusReceiver::ERR_INSTALL_DEVICE_TYPE_NOT_SUPPORTED, ERROR_INSTALL_PARSE_FAILED },
349 { IStatusReceiver::ERR_INSTALL_CHECK_SYSCAP_FAILED_AND_DEVICE_TYPE_NOT_SUPPORTED, ERROR_INSTALL_PARSE_FAILED },
350 { IStatusReceiver::ERR_INSTALL_PARSE_PROFILE_PROP_SIZE_CHECK_ERROR, ERROR_INSTALL_PARSE_FAILED },
351 { IStatusReceiver::ERR_INSTALL_DEPENDENT_MODULE_NOT_EXIST, ERROR_INSTALL_DEPENDENT_MODULE_NOT_EXIST },
352 { IStatusReceiver::ERR_INSTALL_SHARE_APP_LIBRARY_NOT_ALLOWED, ERROR_INSTALL_SHARE_APP_LIBRARY_NOT_ALLOWED },
353 { IStatusReceiver::ERR_INSTALL_COMPATIBLE_POLICY_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
354 { IStatusReceiver::ERR_INSTALL_FILE_IS_SHARED_LIBRARY, ERROR_INSTALL_FILE_IS_SHARED_LIBRARY },
355 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_INTERNAL_ERROR, ERROR_BUNDLE_SERVICE_EXCEPTION },
356 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_INVALID_BUNDLE_NAME, ERROR_BUNDLE_NOT_EXIST },
357 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_INVALID_MODULE_NAME, ERROR_MODULE_NOT_EXIST},
358 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_ERROR_HAP_TYPE, ERROR_INVALID_TYPE },
359 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_ERROR_BUNDLE_TYPE, ERROR_INVALID_TYPE },
360 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_TARGET_BUNDLE_NAME_MISSED, ERROR_INSTALL_PARSE_FAILED },
361 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_TARGET_MODULE_NAME_MISSED, ERROR_INSTALL_PARSE_FAILED },
362 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_TARGET_BUNDLE_NAME_NOT_SAME,
363 ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
364 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_INTERNAL_EXTERNAL_OVERLAY_EXISTED_SIMULTANEOUSLY,
365 ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
366 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_TARGET_PRIORITY_NOT_SAME,
367 ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
368 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_INVALID_PRIORITY, ERROR_INSTALL_PARSE_FAILED },
369 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_INCONSISTENT_VERSION_CODE,
370 ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
371 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_SERVICE_EXCEPTION, ERROR_BUNDLE_SERVICE_EXCEPTION },
372 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_BUNDLE_NAME_SAME_WITH_TARGET_BUNDLE_NAME,
373 ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT},
374 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_NO_SYSTEM_APPLICATION_FOR_EXTERNAL_OVERLAY,
375 ERROR_INSTALL_HAP_OVERLAY_CHECK_FAILED },
376 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_DIFFERENT_SIGNATURE_CERTIFICATE,
377 ERROR_INSTALL_VERIFY_SIGNATURE_FAILED },
378 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_TARGET_BUNDLE_IS_OVERLAY_BUNDLE,
379 ERROR_INSTALL_HAP_OVERLAY_CHECK_FAILED },
380 {IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_TARGET_MODULE_IS_OVERLAY_MODULE,
381 ERROR_INSTALL_HAP_OVERLAY_CHECK_FAILED },
382 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_OVERLAY_TYPE_NOT_SAME,
383 ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
384 { IStatusReceiver::ERR_OVERLAY_INSTALLATION_FAILED_INVALID_BUNDLE_DIR, ERROR_BUNDLE_SERVICE_EXCEPTION },
385 { IStatusReceiver::ERR_APPEXECFWK_UNINSTALL_SHARE_APP_LIBRARY_IS_NOT_EXIST,
386 ERROR_UNINSTALL_SHARE_APP_LIBRARY_IS_NOT_EXIST},
387 { IStatusReceiver::ERR_APPEXECFWK_UNINSTALL_SHARE_APP_LIBRARY_IS_RELIED,
388 ERROR_UNINSTALL_SHARE_APP_LIBRARY_IS_RELIED},
389 { IStatusReceiver::ERR_APPEXECFWK_UNINSTALL_BUNDLE_IS_SHARED_LIBRARY,
390 ERROR_UNINSTALL_BUNDLE_IS_SHARED_BUNDLE},
391 { IStatusReceiver::ERR_INSATLL_CHECK_PROXY_DATA_URI_FAILED,
392 ERROR_INSTALL_WRONG_DATA_PROXY_URI},
393 { IStatusReceiver::ERR_INSATLL_CHECK_PROXY_DATA_PERMISSION_FAILED,
394 ERROR_INSTALL_WRONG_DATA_PROXY_PERMISSION},
395 { IStatusReceiver::ERR_INSTALL_FAILED_DEBUG_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT },
396 { IStatusReceiver::ERR_INSTALL_DISALLOWED, ERROR_DISALLOW_INSTALL},
397 { IStatusReceiver::ERR_INSTALL_ISOLATION_MODE_FAILED, ERROR_INSTALL_WRONG_MODE_ISOLATION },
398 { IStatusReceiver::ERR_UNINSTALL_DISALLOWED, ERROR_DISALLOW_UNINSTALL },
399 { IStatusReceiver::ERR_INSTALL_CODE_SIGNATURE_FAILED, ERROR_INSTALL_CODE_SIGNATURE_FAILED },
400 { IStatusReceiver::ERR_INSTALL_CODE_SIGNATURE_FILE_IS_INVALID, ERROR_INSTALL_CODE_SIGNATURE_FAILED},
401 { IStatusReceiver::ERR_UNINSTALL_FROM_BMS_EXTENSION_FAILED, ERROR_BUNDLE_NOT_EXIST},
402 { IStatusReceiver::ERR_INSTALL_SELF_UPDATE_NOT_MDM, ERROR_INSTALL_SELF_UPDATE_NOT_MDM},
403 { IStatusReceiver::ERR_INSTALL_ENTERPRISE_BUNDLE_NOT_ALLOWED, ERROR_INSTALL_ENTERPRISE_BUNDLE_NOT_ALLOWED},
404 { IStatusReceiver::ERR_INSTALL_EXISTED_ENTERPRISE_BUNDLE_NOT_ALLOWED,
405 ERROR_INSTALL_EXISTED_ENTERPRISE_NOT_ALLOWED_ERROR},
406 { IStatusReceiver::ERR_INSTALL_SELF_UPDATE_BUNDLENAME_NOT_SAME, ERROR_INSTALL_SELF_UPDATE_BUNDLENAME_NOT_SAME},
407 { IStatusReceiver::ERR_INSTALL_GWP_ASAN_ENABLED_NOT_SAME, ERROR_INSTALL_MULTIPLE_HAP_INFO_INCONSISTENT},
408 { IStatusReceiver::ERR_INSTALL_DEBUG_BUNDLE_NOT_ALLOWED, ERROR_INSTALL_DEBUG_BUNDLE_NOT_ALLOWED},
409 { IStatusReceiver::ERR_INSTALL_CHECK_ENCRYPTION_FAILED, ERROR_INSTALL_CODE_SIGNATURE_FAILED },
410 { IStatusReceiver::ERR_INSTALL_CODE_SIGNATURE_DELIVERY_FILE_FAILED, ERROR_INSTALL_CODE_SIGNATURE_FAILED},
411 { IStatusReceiver::ERR_INSTALL_CODE_SIGNATURE_REMOVE_FILE_FAILED, ERROR_INSTALL_CODE_SIGNATURE_FAILED},
412 { IStatusReceiver::ERR_INSTALL_CODE_APP_CONTROLLED_FAILED, ERROR_INSTALL_FAILED_CONTROLLED},
413 { IStatusReceiver::ERR_INSTALL_NATIVE_FAILED, ERROR_INSTALL_NATIVE_FAILED},
414 { IStatusReceiver::ERR_UNINSTALL_NATIVE_FAILED, ERROR_UNINSTALL_NATIVE_FAILED},
415 { IStatusReceiver::ERR_NATIVE_HNP_EXTRACT_FAILED, ERROR_INSTALL_NATIVE_FAILED},
416 { IStatusReceiver::ERR_UNINSTALL_CONTROLLED, ERROR_BUNDLE_CAN_NOT_BE_UNINSTALLED },
417 { IStatusReceiver::ERR_INSTALL_DEBUG_ENCRYPTED_BUNDLE_FAILED, ERROR_INSTALL_PARSE_FAILED }
418 };
419 }
420
ConvertInstallResult(InstallResult &installResult)421 static void ConvertInstallResult(InstallResult &installResult)
422 {
423 APP_LOGD("ConvertInstallResult msg %{public}s, errCode is %{public}d", installResult.resultMsg.c_str(),
424 installResult.resultCode);
425 std::unordered_map<int32_t, int32_t> errCodeMap;
426 CreateErrCodeMap(errCodeMap);
427 auto iter = errCodeMap.find(installResult.resultCode);
428 if (iter != errCodeMap.end()) {
429 installResult.resultCode = iter->second;
430 return;
431 }
432 installResult.resultCode = ERROR_BUNDLE_SERVICE_EXCEPTION;
433 }
434
ParseHashParam(napi_env env, napi_value args, std::string &key, std::string &value)435 static bool ParseHashParam(napi_env env, napi_value args, std::string &key, std::string &value)
436 {
437 APP_LOGD("start to parse moduleName");
438 bool ret = CommonFunc::ParseStringPropertyFromObject(env, args, MODULE_NAME, true, key);
439 if (!ret || key.empty()) {
440 APP_LOGE("param string moduleName is empty");
441 return false;
442 }
443 APP_LOGD("ParseHashParam moduleName=%{public}s", key.c_str());
444
445 APP_LOGD("start to parse hashValue");
446 ret = CommonFunc::ParseStringPropertyFromObject(env, args, HASH_VALUE, true, value);
447 if (!ret || value.empty()) {
448 APP_LOGE("param string hashValue is empty");
449 return false;
450 }
451 APP_LOGD("ParseHashParam hashValue=%{public}s", value.c_str());
452 return true;
453 }
454
ParseHashParams(napi_env env, napi_value args, std::map<std::string, std::string> &hashParams)455 static bool ParseHashParams(napi_env env, napi_value args, std::map<std::string, std::string> &hashParams)
456 {
457 APP_LOGD("start to parse hashParams");
458 std::vector<napi_value> valueVec;
459 bool res = CommonFunc::ParsePropertyArray(env, args, HASH_PARAMS, valueVec);
460 if (!res) {
461 APP_LOGW("hashParams type error,using default value");
462 return true;
463 }
464 if (valueVec.empty()) {
465 APP_LOGW("hashParams is empty,using default value");
466 return true;
467 }
468 for (const auto &property : valueVec) {
469 std::string key;
470 std::string value;
471 if (!ParseHashParam(env, property, key, value)) {
472 APP_LOGE("parse hash param failed");
473 return false;
474 }
475 if (hashParams.find(key) != hashParams.end()) {
476 APP_LOGE("moduleName(%{public}s) is duplicate", key.c_str());
477 return false;
478 }
479 hashParams.emplace(key, value);
480 }
481 return true;
482 }
483
ParseVerifyCodeParam(napi_env env, napi_value args, std::string &key, std::string &value)484 static bool ParseVerifyCodeParam(napi_env env, napi_value args, std::string &key, std::string &value)
485 {
486 APP_LOGD("start to parse moduleName");
487 bool ret = CommonFunc::ParseStringPropertyFromObject(env, args, MODULE_NAME, true, key);
488 if (!ret || key.empty()) {
489 APP_LOGE("param string moduleName is empty");
490 return false;
491 }
492 APP_LOGD("ParseVerifyCodeParam moduleName is %{public}s", key.c_str());
493
494 APP_LOGD("start to parse signatureFilePath");
495 ret = CommonFunc::ParseStringPropertyFromObject(env, args, SIGNATURE_FILE_PATH, true, value);
496 if (!ret || value.empty()) {
497 APP_LOGE("param string signatureFilePath is empty");
498 return false;
499 }
500 APP_LOGD("ParseVerifyCodeParam signatureFilePath is %{public}s", value.c_str());
501 return true;
502 }
503
ParseVerifyCodeParams(napi_env env, napi_value args, std::map<std::string, std::string> &verifyCodeParams)504 static bool ParseVerifyCodeParams(napi_env env, napi_value args, std::map<std::string, std::string> &verifyCodeParams)
505 {
506 APP_LOGD("start to parse verifyCodeParams");
507 std::vector<napi_value> valueVec;
508 bool res = CommonFunc::ParsePropertyArray(env, args, VERIFY_CODE_PARAM, valueVec);
509 if (!res) {
510 APP_LOGW("verifyCodeParams type error, using default value");
511 return true;
512 }
513 if (valueVec.empty()) {
514 APP_LOGW("verifyCodeParams is empty, using default value");
515 return true;
516 }
517 for (const auto &property : valueVec) {
518 std::string key;
519 std::string value;
520 if (!ParseVerifyCodeParam(env, property, key, value)) {
521 APP_LOGE("parse verify code param failed");
522 return false;
523 }
524 if (verifyCodeParams.find(key) != verifyCodeParams.end()) {
525 APP_LOGE("moduleName(%{public}s) is duplicate", key.c_str());
526 return false;
527 }
528 verifyCodeParams.emplace(key, value);
529 }
530 return true;
531 }
532
ParsePgoParam(napi_env env, napi_value args, std::string &key, std::string &value)533 static bool ParsePgoParam(napi_env env, napi_value args, std::string &key, std::string &value)
534 {
535 APP_LOGD("start to parse moduleName");
536 bool ret = CommonFunc::ParseStringPropertyFromObject(env, args, MODULE_NAME, true, key);
537 if (!ret || key.empty()) {
538 APP_LOGE("param string moduleName is empty");
539 return false;
540 }
541 APP_LOGD("ParsePgoParam moduleName is %{public}s", key.c_str());
542
543 APP_LOGD("start to parse pgoFilePath");
544 ret = CommonFunc::ParseStringPropertyFromObject(env, args, PGO_FILE_PATH, true, value);
545 if (!ret || value.empty()) {
546 APP_LOGE("param string pgoFilePath is empty");
547 return false;
548 }
549 APP_LOGD("ParsePgoParam pgoFilePath is %{public}s", value.c_str());
550 return true;
551 }
552
ParsePgoParams(napi_env env, napi_value args, std::map<std::string, std::string> &pgoParams)553 static bool ParsePgoParams(napi_env env, napi_value args, std::map<std::string, std::string> &pgoParams)
554 {
555 APP_LOGD("start to parse pgoParams");
556 std::vector<napi_value> valueVec;
557 bool res = CommonFunc::ParsePropertyArray(env, args, PGO_PARAM, valueVec);
558 if (!res) {
559 APP_LOGW("pgoParams type error, using default value");
560 return true;
561 }
562 if (valueVec.empty()) {
563 APP_LOGW("pgoParams is empty, using default value");
564 return true;
565 }
566 for (const auto &property : valueVec) {
567 std::string key;
568 std::string value;
569 if (!ParsePgoParam(env, property, key, value)) {
570 APP_LOGW("parse pgo param failed");
571 continue;
572 }
573 pgoParams.emplace(key, value);
574 }
575 return true;
576 }
577
ParseBundleName(napi_env env, napi_value args, std::string &bundleName)578 static bool ParseBundleName(napi_env env, napi_value args, std::string &bundleName)
579 {
580 APP_LOGD("start to parse bundleName");
581 PropertyInfo propertyInfo = {
582 .propertyName = BUNDLE_NAME,
583 .isNecessary = true,
584 .propertyType = napi_string
585 };
586 napi_value property = nullptr;
587 bool res = CommonFunc::ParsePropertyFromObject(env, args, propertyInfo, property);
588 if (!res) {
589 APP_LOGE("parse bundleName failed, bundleName is %{public}s", bundleName.c_str());
590 return res;
591 }
592 if (property != nullptr) {
593 if (!CommonFunc::ParseString(env, property, bundleName)) {
594 APP_LOGE("ParseString failed");
595 return false;
596 }
597 }
598 APP_LOGD("param bundleName is %{public}s", bundleName.c_str());
599 return true;
600 }
601
ParseModuleName(napi_env env, napi_value args, std::string &moduleName)602 static bool ParseModuleName(napi_env env, napi_value args, std::string &moduleName)
603 {
604 APP_LOGD("start to parse moduleName");
605 PropertyInfo propertyInfo = {
606 .propertyName = MODULE_NAME,
607 .isNecessary = false,
608 .propertyType = napi_string
609 };
610 napi_value property = nullptr;
611 bool res = CommonFunc::ParsePropertyFromObject(env, args, propertyInfo, property);
612 if (!res) {
613 APP_LOGE("parse moduleName failed");
614 return res;
615 }
616 if (property != nullptr) {
617 if (!CommonFunc::ParseString(env, property, moduleName)) {
618 APP_LOGE("ParseString failed");
619 return false;
620 }
621 }
622 return true;
623 }
624
ParseVersionCode(napi_env env, napi_value args, int32_t &versionCode)625 static bool ParseVersionCode(napi_env env, napi_value args, int32_t &versionCode)
626 {
627 APP_LOGD("start to parse versionCode");
628 PropertyInfo propertyInfo = {
629 .propertyName = VERSION_CODE,
630 .isNecessary = false,
631 .propertyType = napi_number
632 };
633 napi_value property = nullptr;
634 bool res = CommonFunc::ParsePropertyFromObject(env, args, propertyInfo, property);
635 if (!res) {
636 APP_LOGE("parse versionCode failed");
637 return res;
638 }
639 if (property != nullptr) {
640 PARSE_PROPERTY(env, property, int32, versionCode);
641 }
642 APP_LOGD("param versionCode is %{public}d", versionCode);
643 return true;
644 }
645
ParseUserId(napi_env env, napi_value args, int32_t &userId)646 static bool ParseUserId(napi_env env, napi_value args, int32_t &userId)
647 {
648 APP_LOGD("start to parse userId");
649 PropertyInfo propertyInfo = {
650 .propertyName = USER_ID,
651 .isNecessary = false,
652 .propertyType = napi_number
653 };
654 napi_value property = nullptr;
655 bool res = CommonFunc::ParsePropertyFromObject(env, args, propertyInfo, property);
656 if (!res) {
657 APP_LOGE("parse userId failed");
658 return res;
659 }
660 if (property != nullptr) {
661 PARSE_PROPERTY(env, property, int32, userId);
662 }
663 APP_LOGD("param userId is %{public}d", userId);
664 return true;
665 }
666
ParseAppIndex(napi_env env, napi_value args, int32_t &appIndex)667 static bool ParseAppIndex(napi_env env, napi_value args, int32_t &appIndex)
668 {
669 APP_LOGD("start to parse appIndex");
670 PropertyInfo propertyInfo = {
671 .propertyName = APP_INDEX,
672 .isNecessary = true,
673 .propertyType = napi_number
674 };
675 napi_value property = nullptr;
676 bool res = CommonFunc::ParsePropertyFromObject(env, args, propertyInfo, property);
677 if (!res) {
678 APP_LOGE("parse appIndex failed");
679 return res;
680 }
681 if (property != nullptr) {
682 PARSE_PROPERTY(env, property, int32, appIndex);
683 }
684 APP_LOGD("param appIndex is %{public}d", appIndex);
685 return true;
686 }
687
ParseInstallFlag(napi_env env, napi_value args, InstallFlag &installFlag)688 static bool ParseInstallFlag(napi_env env, napi_value args, InstallFlag &installFlag)
689 {
690 APP_LOGD("start to parse installFlag");
691 PropertyInfo propertyInfo = {
692 .propertyName = INSTALL_FLAG,
693 .isNecessary = false,
694 .propertyType = napi_number
695 };
696 napi_value property = nullptr;
697 bool res = CommonFunc::ParsePropertyFromObject(env, args, propertyInfo, property);
698 if (!res) {
699 APP_LOGE("parse installFlag failed");
700 return res;
701 }
702
703 if (property != nullptr) {
704 int32_t flag = 0;
705 PARSE_PROPERTY(env, property, int32, flag);
706 APP_LOGD("param installFlag is %{public}d", flag);
707 if ((flag != static_cast<int32_t>(OHOS::AppExecFwk::InstallFlag::NORMAL)) &&
708 (flag != static_cast<int32_t>(OHOS::AppExecFwk::InstallFlag::REPLACE_EXISTING)) &&
709 (flag != static_cast<int32_t>(OHOS::AppExecFwk::InstallFlag::FREE_INSTALL))) {
710 APP_LOGE("invalid installFlag param");
711 return false;
712 }
713 installFlag = static_cast<OHOS::AppExecFwk::InstallFlag>(flag);
714 }
715 return true;
716 }
717
ParseIsKeepData(napi_env env, napi_value args, bool &isKeepData)718 static bool ParseIsKeepData(napi_env env, napi_value args, bool &isKeepData)
719 {
720 APP_LOGD("start to parse isKeepData");
721 PropertyInfo propertyInfo = {
722 .propertyName = IS_KEEP_DATA,
723 .isNecessary = false,
724 .propertyType = napi_boolean
725 };
726 napi_value property = nullptr;
727 bool res = CommonFunc::ParsePropertyFromObject(env, args, propertyInfo, property);
728 if (!res) {
729 APP_LOGE("parse isKeepData failed");
730 return res;
731 }
732 if (property != nullptr) {
733 PARSE_PROPERTY(env, property, bool, isKeepData);
734 }
735 APP_LOGD("param isKeepData is %{public}d", isKeepData);
736 return true;
737 }
738
ParseCrowdtestDeadline(napi_env env, napi_value args, int64_t &crowdtestDeadline)739 static bool ParseCrowdtestDeadline(napi_env env, napi_value args, int64_t &crowdtestDeadline)
740 {
741 APP_LOGD("start to parse crowdtestDeadline");
742 PropertyInfo propertyInfo = {
743 .propertyName = CROWD_TEST_DEADLINE,
744 .isNecessary = false,
745 .propertyType = napi_number
746 };
747 napi_value property = nullptr;
748 bool res = CommonFunc::ParsePropertyFromObject(env, args, propertyInfo, property);
749 if (!res) {
750 APP_LOGE("parse crowdtestDeadline failed");
751 return res;
752 }
753 if (property != nullptr) {
754 PARSE_PROPERTY(env, property, int64, crowdtestDeadline);
755 }
756 return true;
757 }
758
ParseSharedBundleDirPaths(napi_env env, napi_value args, std::vector<std::string> &sharedBundleDirPaths)759 static bool ParseSharedBundleDirPaths(napi_env env, napi_value args, std::vector<std::string> &sharedBundleDirPaths)
760 {
761 APP_LOGD("start to parse sharedBundleDirPaths");
762 std::vector<napi_value> valueVec;
763 bool res = CommonFunc::ParsePropertyArray(env, args, SHARED_BUNDLE_DIR_PATHS, valueVec);
764 if (!res) {
765 APP_LOGE("parse sharedBundleDirPaths failed");
766 return res;
767 }
768 if (valueVec.empty()) {
769 APP_LOGD("sharedBundleDirPaths is empty");
770 return true;
771 }
772 for (const auto &value : valueVec) {
773 std::string path;
774 if (!CommonFunc::ParseString(env, value, path)) {
775 APP_LOGE("parse sharedBundleDirPaths element failed");
776 return false;
777 }
778 sharedBundleDirPaths.emplace_back(path);
779 }
780 return true;
781 }
782
ParseSpecifiedDistributionType(napi_env env, napi_value args, std::string &specifiedDistributionType)783 static bool ParseSpecifiedDistributionType(napi_env env, napi_value args, std::string &specifiedDistributionType)
784 {
785 APP_LOGD("start to parse specifiedDistributionType");
786 PropertyInfo propertyInfo = {
787 .propertyName = SPECIFIED_DISTRIBUTION_TYPE,
788 .isNecessary = false,
789 .propertyType = napi_string
790 };
791 napi_value property = nullptr;
792 bool res = CommonFunc::ParsePropertyFromObject(env, args, propertyInfo, property);
793 if (!res) {
794 APP_LOGE("parse specifiedDistributionType failed");
795 return res;
796 }
797 if (property != nullptr) {
798 if (!CommonFunc::ParseString(env, property, specifiedDistributionType)) {
799 APP_LOGE("ParseString failed");
800 return false;
801 }
802 }
803 APP_LOGD("param specifiedDistributionType is %{public}s", specifiedDistributionType.c_str());
804 return true;
805 }
806
ParseAdditionalInfo(napi_env env, napi_value args, std::string &additionalInfo)807 static bool ParseAdditionalInfo(napi_env env, napi_value args, std::string &additionalInfo)
808 {
809 APP_LOGD("start to parse the additionalInfo");
810 PropertyInfo propertyInfo = {
811 .propertyName = ADDITIONAL_INFO,
812 .isNecessary = false,
813 .propertyType = napi_string
814 };
815 napi_value property = nullptr;
816 bool res = CommonFunc::ParsePropertyFromObject(env, args, propertyInfo, property);
817 if (!res) {
818 APP_LOGE("parse additionalInfo failed");
819 return res;
820 }
821 if (property != nullptr) {
822 if (!CommonFunc::ParseString(env, property, additionalInfo)) {
823 APP_LOGE("ParseString failed");
824 return false;
825 }
826 }
827 APP_LOGD("param additionalInfo is %{public}s", additionalInfo.c_str());
828 return true;
829 }
830
CheckInstallParam(napi_env env, InstallParam &installParam)831 static bool CheckInstallParam(napi_env env, InstallParam &installParam)
832 {
833 if (installParam.specifiedDistributionType.size() > SPECIFIED_DISTRIBUTION_TYPE_MAX_SIZE) {
834 APP_LOGE("Parse specifiedDistributionType size failed");
835 BusinessError::ThrowError(env, ERROR_PARAM_CHECK_ERROR,
836 "BusinessError 401: The size of specifiedDistributionType is greater than 128");
837 return false;
838 }
839 if (installParam.additionalInfo.size() > ADDITIONAL_INFO_MAX_SIZE) {
840 APP_LOGE("Parse additionalInfo size failed");
841 BusinessError::ThrowError(env, ERROR_PARAM_CHECK_ERROR,
842 "BusinessError 401: The size of additionalInfo is greater than 3000");
843 return false;
844 }
845 return true;
846 }
847
ParseInstallParam(napi_env env, napi_value args, InstallParam &installParam)848 static bool ParseInstallParam(napi_env env, napi_value args, InstallParam &installParam)
849 {
850 if (!ParseHashParams(env, args, installParam.hashParams)) {
851 return false;
852 }
853 if (!ParseVerifyCodeParams(env, args, installParam.verifyCodeParams)) {
854 return false;
855 }
856 if (!ParsePgoParams(env, args, installParam.pgoParams)) {
857 return false;
858 }
859 if (!ParseUserId(env, args, installParam.userId)) {
860 APP_LOGW("Parse userId failed,using default value");
861 }
862 if (!ParseInstallFlag(env, args, installParam.installFlag)) {
863 APP_LOGW("Parse installFlag failed,using default value");
864 }
865 if (!ParseIsKeepData(env, args, installParam.isKeepData)) {
866 APP_LOGW("Parse isKeepData failed,using default value");
867 }
868 if (!ParseCrowdtestDeadline(env, args, installParam.crowdtestDeadline)) {
869 APP_LOGW("Parse crowdtestDeadline failed,using default value");
870 }
871 if (!ParseSharedBundleDirPaths(env, args, installParam.sharedBundleDirPaths)) {
872 APP_LOGW("Parse sharedBundleDirPaths failed,using default value");
873 }
874 if (!ParseSpecifiedDistributionType(env, args, installParam.specifiedDistributionType)) {
875 APP_LOGW("Parse specifiedDistributionType failed,using default value");
876 }
877 if (!ParseAdditionalInfo(env, args, installParam.additionalInfo)) {
878 APP_LOGW("Parse additionalInfo failed,using default value");
879 }
880 return true;
881 }
882
ParseUninstallParam(napi_env env, napi_value args, UninstallParam &uninstallParam)883 static bool ParseUninstallParam(napi_env env, napi_value args, UninstallParam &uninstallParam)
884 {
885 if (!ParseBundleName(env, args, uninstallParam.bundleName) ||
886 !ParseModuleName(env, args, uninstallParam.moduleName) ||
887 !ParseVersionCode(env, args, uninstallParam.versionCode) ||
888 !ParseUserId(env, args, uninstallParam.userId)) {
889 APP_LOGE("Parse UninstallParam faied");
890 return false;
891 }
892 return true;
893 }
894
CreateProxyErrCode(std::unordered_map<int32_t, int32_t> &errCodeMap)895 static void CreateProxyErrCode(std::unordered_map<int32_t, int32_t> &errCodeMap)
896 {
897 errCodeMap = {
898 { ERR_APPEXECFWK_INSTALL_PARAM_ERROR, IStatusReceiver::ERR_INSTALL_PARAM_ERROR },
899 { ERR_APPEXECFWK_INSTALL_INTERNAL_ERROR, IStatusReceiver::ERR_INSTALL_INTERNAL_ERROR },
900 { ERR_APPEXECFWK_INSTALL_FILE_PATH_INVALID, IStatusReceiver::ERR_INSTALL_FILE_PATH_INVALID },
901 { ERR_APPEXECFWK_INSTALL_DISK_MEM_INSUFFICIENT, IStatusReceiver::ERR_INSTALL_DISK_MEM_INSUFFICIENT },
902 { ERR_BUNDLEMANAGER_INSTALL_CODE_SIGNATURE_FILE_IS_INVALID,
903 IStatusReceiver::ERR_INSTALL_CODE_SIGNATURE_FILE_IS_INVALID}
904 };
905 }
906
InstallExecuter(napi_env env, void *data)907 void InstallExecuter(napi_env env, void *data)
908 {
909 AsyncInstallCallbackInfo *asyncCallbackInfo = reinterpret_cast<AsyncInstallCallbackInfo *>(data);
910 if (asyncCallbackInfo == nullptr) {
911 APP_LOGE("asyncCallbackInfo is nullptr");
912 return;
913 }
914 const std::vector<std::string> bundleFilePath = asyncCallbackInfo->hapFiles;
915 InstallResult &installResult = asyncCallbackInfo->installResult;
916 if (bundleFilePath.empty() && asyncCallbackInfo->installParam.sharedBundleDirPaths.empty()) {
917 installResult.resultCode = static_cast<int32_t>(IStatusReceiver::ERR_INSTALL_FILE_PATH_INVALID);
918 return;
919 }
920 auto iBundleInstaller = CommonFunc::GetBundleInstaller();
921 if ((iBundleInstaller == nullptr) || (iBundleInstaller->AsObject() == nullptr)) {
922 APP_LOGE("can not get iBundleInstaller");
923 installResult.resultCode = static_cast<int32_t>(IStatusReceiver::ERR_INSTALL_INTERNAL_ERROR);
924 return;
925 }
926
927 sptr<InstallerCallback> callback = new (std::nothrow) InstallerCallback();
928 sptr<BundleDeathRecipient> recipient(new (std::nothrow) BundleDeathRecipient(callback));
929 if (callback == nullptr || recipient == nullptr) {
930 APP_LOGE("callback or death recipient is nullptr");
931 installResult.resultCode = static_cast<int32_t>(IStatusReceiver::ERR_INSTALL_INTERNAL_ERROR);
932 return;
933 }
934 iBundleInstaller->AsObject()->AddDeathRecipient(recipient);
935
936 ErrCode res = iBundleInstaller->StreamInstall(bundleFilePath, asyncCallbackInfo->installParam, callback);
937 if (res == ERR_OK) {
938 installResult.resultCode = callback->GetResultCode();
939 APP_LOGD("InnerInstall resultCode %{public}d", installResult.resultCode);
940 installResult.resultMsg = callback->GetResultMsg();
941 APP_LOGD("InnerInstall resultMsg %{public}s", installResult.resultMsg.c_str());
942 return;
943 }
944 APP_LOGE("install failed due to %{public}d", res);
945 std::unordered_map<int32_t, int32_t> proxyErrCodeMap;
946 CreateProxyErrCode(proxyErrCodeMap);
947 if (proxyErrCodeMap.find(res) != proxyErrCodeMap.end()) {
948 installResult.resultCode = proxyErrCodeMap.at(res);
949 } else {
950 installResult.resultCode = IStatusReceiver::ERR_INSTALL_INTERNAL_ERROR;
951 }
952 }
953
GetFunctionName(const InstallOption &option)954 static std::string GetFunctionName(const InstallOption &option)
955 {
956 if (option == InstallOption::INSTALL) {
957 return RESOURCE_NAME_OF_INSTALL;
958 } else if (option == InstallOption::RECOVER) {
959 return RESOURCE_NAME_OF_RECOVER;
960 } else if (option == InstallOption::UNINSTALL) {
961 return RESOURCE_NAME_OF_UNINSTALL;
962 } else if (option == InstallOption::UPDATE_BUNDLE_FOR_SELF) {
963 return RESOURCE_NAME_OF_UPDATE_BUNDLE_FOR_SELF;
964 } else if (option == InstallOption::UNINSTALL_AND_RECOVER) {
965 return RESOURCE_NAME_OF_UNINSTALL_AND_RECOVER;
966 }
967 return EMPTY_STRING;
968 }
969
OperationCompleted(napi_env env, napi_status status, void *data)970 void OperationCompleted(napi_env env, napi_status status, void *data)
971 {
972 AsyncInstallCallbackInfo *asyncCallbackInfo = reinterpret_cast<AsyncInstallCallbackInfo *>(data);
973 std::unique_ptr<AsyncInstallCallbackInfo> callbackPtr {asyncCallbackInfo};
974 napi_value result[CALLBACK_PARAM_SIZE] = {0};
975 ConvertInstallResult(callbackPtr->installResult);
976 if (callbackPtr->installResult.resultCode != SUCCESS) {
977 switch (callbackPtr->option) {
978 case InstallOption::INSTALL:
979 result[FIRST_PARAM] = BusinessError::CreateCommonError(env, callbackPtr->installResult.resultCode,
980 RESOURCE_NAME_OF_INSTALL, INSTALL_PERMISSION);
981 break;
982 case InstallOption::RECOVER:
983 result[FIRST_PARAM] = BusinessError::CreateCommonError(env, callbackPtr->installResult.resultCode,
984 RESOURCE_NAME_OF_RECOVER, RECOVER_PERMISSION);
985 break;
986 case InstallOption::UNINSTALL:
987 result[FIRST_PARAM] = BusinessError::CreateCommonError(env, callbackPtr->installResult.resultCode,
988 RESOURCE_NAME_OF_UNINSTALL, UNINSTALL_PERMISSION);
989 break;
990 case InstallOption::UPDATE_BUNDLE_FOR_SELF:
991 result[FIRST_PARAM] = BusinessError::CreateCommonError(env, callbackPtr->installResult.resultCode,
992 RESOURCE_NAME_OF_UPDATE_BUNDLE_FOR_SELF, INSTALL_SELF_PERMISSION);
993 break;
994 case InstallOption::UNINSTALL_AND_RECOVER:
995 result[FIRST_PARAM] = BusinessError::CreateCommonError(env, callbackPtr->installResult.resultCode,
996 RESOURCE_NAME_OF_UNINSTALL_AND_RECOVER, UNINSTALL_PERMISSION);
997 break;
998 default:
999 break;
1000 }
1001 } else {
1002 NAPI_CALL_RETURN_VOID(env, napi_get_null(env, &result[FIRST_PARAM]));
1003 }
1004 callbackPtr->err = callbackPtr->installResult.resultCode;
1005 APP_LOGI("installer callback");
1006 CommonFunc::NapiReturnDeferred<AsyncInstallCallbackInfo>(env, asyncCallbackInfo, result, ARGS_SIZE_ONE);
1007 }
1008
1009 /**
1010 * Promise and async callback
1011 */
Install(napi_env env, napi_callback_info info)1012 napi_value Install(napi_env env, napi_callback_info info)
1013 {
1014 APP_LOGI("Install called");
1015 // obtain arguments of install interface
1016 NapiArg args(env, info);
1017 if (!args.Init(ARGS_SIZE_ONE, ARGS_SIZE_THREE)) {
1018 APP_LOGE("init param failed");
1019 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1020 return nullptr;
1021 }
1022 auto argc = args.GetMaxArgc();
1023 APP_LOGD("the number of argc is %{public}zu", argc);
1024 if (argc < ARGS_SIZE_ONE) {
1025 APP_LOGE("the params number is incorrect");
1026 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1027 return nullptr;
1028 }
1029 std::unique_ptr<AsyncInstallCallbackInfo> callbackPtr = std::make_unique<AsyncInstallCallbackInfo>(env);
1030 callbackPtr->option = InstallOption::INSTALL;
1031 for (size_t i = 0; i < argc; ++i) {
1032 napi_valuetype valueType = napi_undefined;
1033 napi_typeof(env, args[i], &valueType);
1034 if (i == ARGS_POS_ZERO) {
1035 if (!CommonFunc::ParseStringArray(env, callbackPtr->hapFiles, args[i])) {
1036 APP_LOGE("Flags %{public}s invalid", callbackPtr->bundleName.c_str());
1037 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, PARAMETERS, CORRESPONDING_TYPE);
1038 return nullptr;
1039 }
1040 } else if (i == ARGS_POS_ONE) {
1041 if (valueType == napi_function) {
1042 NAPI_CALL(env, napi_create_reference(env, args[i], NAPI_RETURN_ONE, &callbackPtr->callback));
1043 break;
1044 }
1045 if (valueType == napi_object && !ParseInstallParam(env, args[i], callbackPtr->installParam)) {
1046 APP_LOGE("Parse installParam failed");
1047 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, PARAMETERS, CORRESPONDING_TYPE);
1048 return nullptr;
1049 }
1050 } else if (i == ARGS_POS_TWO) {
1051 if (valueType == napi_function) {
1052 NAPI_CALL(env, napi_create_reference(env, args[i], NAPI_RETURN_ONE, &callbackPtr->callback));
1053 break;
1054 }
1055 } else {
1056 APP_LOGE("param check error");
1057 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, PARAMETERS, CORRESPONDING_TYPE);
1058 return nullptr;
1059 }
1060 }
1061 if (!CheckInstallParam(env, callbackPtr->installParam)) {
1062 return nullptr;
1063 }
1064 if (callbackPtr->hapFiles.empty() && !callbackPtr->installParam.verifyCodeParams.empty()) {
1065 BusinessError::ThrowError(env, ERROR_PARAM_CHECK_ERROR, HAPS_FILE_NEEDED);
1066 return nullptr;
1067 }
1068 auto promise = CommonFunc::AsyncCallNativeMethod(env, callbackPtr.get(), RESOURCE_NAME_OF_INSTALL, InstallExecuter,
1069 OperationCompleted);
1070 callbackPtr.release();
1071 APP_LOGI("call Install done");
1072 return promise;
1073 }
1074
UninstallOrRecoverExecuter(napi_env env, void *data)1075 void UninstallOrRecoverExecuter(napi_env env, void *data)
1076 {
1077 AsyncInstallCallbackInfo *asyncCallbackInfo = reinterpret_cast<AsyncInstallCallbackInfo *>(data);
1078 if (asyncCallbackInfo == nullptr) {
1079 APP_LOGE("asyncCallbackInfo is nullptr");
1080 return;
1081 }
1082 const std::string bundleName = asyncCallbackInfo->bundleName;
1083 InstallResult &installResult = asyncCallbackInfo->installResult;
1084 if (bundleName.empty()) {
1085 installResult.resultCode = static_cast<int32_t>(IStatusReceiver::ERR_RECOVER_INVALID_BUNDLE_NAME);
1086 return;
1087 }
1088 auto iBundleInstaller = CommonFunc::GetBundleInstaller();
1089 if ((iBundleInstaller == nullptr) || (iBundleInstaller->AsObject() == nullptr)) {
1090 APP_LOGE("can not get iBundleInstaller");
1091 installResult.resultCode = static_cast<int32_t>(IStatusReceiver::ERR_INSTALL_INTERNAL_ERROR);
1092 return;
1093 }
1094
1095 sptr<InstallerCallback> callback = new (std::nothrow) InstallerCallback();
1096 sptr<BundleDeathRecipient> recipient(new (std::nothrow) BundleDeathRecipient(callback));
1097 if (callback == nullptr || recipient == nullptr) {
1098 APP_LOGE("callback or death recipient is nullptr");
1099 installResult.resultCode = static_cast<int32_t>(IStatusReceiver::ERR_INSTALL_INTERNAL_ERROR);
1100 return;
1101 }
1102 iBundleInstaller->AsObject()->AddDeathRecipient(recipient);
1103 if (asyncCallbackInfo->option == InstallOption::RECOVER) {
1104 iBundleInstaller->Recover(bundleName, asyncCallbackInfo->installParam, callback);
1105 } else if (asyncCallbackInfo->option == InstallOption::UNINSTALL) {
1106 iBundleInstaller->Uninstall(bundleName, asyncCallbackInfo->installParam, callback);
1107 } else {
1108 APP_LOGE("error install option");
1109 installResult.resultCode = static_cast<int32_t>(IStatusReceiver::ERR_INSTALL_INTERNAL_ERROR);
1110 return;
1111 }
1112 installResult.resultMsg = callback->GetResultMsg();
1113 APP_LOGD("InnerRecover resultMsg %{public}s", installResult.resultMsg.c_str());
1114 installResult.resultCode = callback->GetResultCode();
1115 APP_LOGD("InnerRecover resultCode %{public}d", installResult.resultCode);
1116 }
1117
UninstallByUninstallParamExecuter(napi_env env, void* data)1118 void UninstallByUninstallParamExecuter(napi_env env, void* data)
1119 {
1120 AsyncInstallCallbackInfo *asyncCallbackInfo = reinterpret_cast<AsyncInstallCallbackInfo *>(data);
1121 if (asyncCallbackInfo == nullptr) {
1122 APP_LOGE("asyncCallbackInfo is nullptr");
1123 return;
1124 }
1125 const std::string bundleName = asyncCallbackInfo->uninstallParam.bundleName;
1126 InstallResult &installResult = asyncCallbackInfo->installResult;
1127 if (bundleName.empty()) {
1128 installResult.resultCode =
1129 static_cast<int32_t>(IStatusReceiver::ERR_APPEXECFWK_UNINSTALL_SHARE_APP_LIBRARY_IS_NOT_EXIST);
1130 return;
1131 }
1132 auto iBundleInstaller = CommonFunc::GetBundleInstaller();
1133 if ((iBundleInstaller == nullptr) || (iBundleInstaller->AsObject() == nullptr)) {
1134 APP_LOGE("can not get iBundleInstaller");
1135 installResult.resultCode = static_cast<int32_t>(IStatusReceiver::ERR_INSTALL_INTERNAL_ERROR);
1136 return;
1137 }
1138 sptr<InstallerCallback> callback = new (std::nothrow) InstallerCallback();
1139 sptr<BundleDeathRecipient> recipient(new (std::nothrow) BundleDeathRecipient(callback));
1140 if (callback == nullptr || recipient == nullptr) {
1141 APP_LOGE("callback or death recipient is nullptr");
1142 installResult.resultCode = static_cast<int32_t>(IStatusReceiver::ERR_INSTALL_INTERNAL_ERROR);
1143 return;
1144 }
1145 iBundleInstaller->AsObject()->AddDeathRecipient(recipient);
1146 iBundleInstaller->Uninstall(asyncCallbackInfo->uninstallParam, callback);
1147 installResult.resultMsg = callback->GetResultMsg();
1148 installResult.resultCode = callback->GetResultCode();
1149 }
1150
UninstallByUninstallParam(napi_env env, napi_callback_info info, std::unique_ptr<AsyncInstallCallbackInfo> &callbackPtr)1151 napi_value UninstallByUninstallParam(napi_env env, napi_callback_info info,
1152 std::unique_ptr<AsyncInstallCallbackInfo> &callbackPtr)
1153 {
1154 NapiArg args(env, info);
1155 if (!args.Init(ARGS_SIZE_ONE, ARGS_SIZE_TWO)) {
1156 APP_LOGE("init param failed");
1157 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1158 return nullptr;
1159 }
1160 for (size_t i = 0; i < args.GetMaxArgc(); ++i) {
1161 napi_valuetype valueType = napi_undefined;
1162 napi_typeof(env, args[i], &valueType);
1163 if (i == ARGS_POS_ZERO) {
1164 if (!ParseUninstallParam(env, args[i], callbackPtr->uninstallParam)) {
1165 APP_LOGE("parse uninstallParam failed");
1166 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, PARAMETERS, CORRESPONDING_TYPE);
1167 return nullptr;
1168 }
1169 } else if ((i == ARGS_POS_ONE) && (valueType == napi_function)) {
1170 NAPI_CALL(env, napi_create_reference(env, args[i], NAPI_RETURN_ONE, &callbackPtr->callback));
1171 break;
1172 } else {
1173 APP_LOGE("param check error");
1174 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, PARAMETERS, CORRESPONDING_TYPE);
1175 return nullptr;
1176 }
1177 }
1178 auto promise = CommonFunc::AsyncCallNativeMethod(env, callbackPtr.get(), GetFunctionName(callbackPtr->option),
1179 UninstallByUninstallParamExecuter, OperationCompleted);
1180 callbackPtr.release();
1181 return promise;
1182 }
1183
UninstallOrRecover(napi_env env, napi_callback_info info, std::unique_ptr<AsyncInstallCallbackInfo> &callbackPtr)1184 napi_value UninstallOrRecover(napi_env env, napi_callback_info info,
1185 std::unique_ptr<AsyncInstallCallbackInfo> &callbackPtr)
1186 {
1187 APP_LOGD("UninstallOrRecover by bundleName called");
1188 // obtain arguments of install interface
1189 NapiArg args(env, info);
1190 if (!args.Init(ARGS_SIZE_ONE, ARGS_SIZE_THREE)) {
1191 APP_LOGE("init param failed");
1192 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1193 return nullptr;
1194 }
1195
1196 auto argc = args.GetMaxArgc();
1197 APP_LOGD("the number of argc is %{public}zu", argc);
1198 if (argc < ARGS_SIZE_ONE) {
1199 APP_LOGE("the params number is incorrect");
1200 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1201 return nullptr;
1202 }
1203
1204 for (size_t i = 0; i < args.GetMaxArgc(); ++i) {
1205 napi_valuetype valueType = napi_undefined;
1206 napi_typeof(env, args[i], &valueType);
1207 if (i == ARGS_POS_ZERO) {
1208 if (!CommonFunc::ParseString(env, args[i], callbackPtr->bundleName)) {
1209 APP_LOGE("Flags %{public}s invalid", callbackPtr->bundleName.c_str());
1210 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, PARAMETERS, CORRESPONDING_TYPE);
1211 return nullptr;
1212 }
1213 } else if (i == ARGS_POS_ONE) {
1214 if (valueType == napi_function) {
1215 NAPI_CALL(env, napi_create_reference(env, args[i], NAPI_RETURN_ONE, &callbackPtr->callback));
1216 break;
1217 }
1218 if (valueType == napi_object && !ParseInstallParam(env, args[i], callbackPtr->installParam)) {
1219 APP_LOGE("Parse installParam.hashParams failed");
1220 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, PARAMETERS, CORRESPONDING_TYPE);
1221 return nullptr;
1222 }
1223 } else if (i == ARGS_POS_TWO) {
1224 if (valueType == napi_function) {
1225 NAPI_CALL(env, napi_create_reference(env, args[i], NAPI_RETURN_ONE, &callbackPtr->callback));
1226 break;
1227 }
1228 } else {
1229 APP_LOGE("param check error");
1230 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, PARAMETERS, CORRESPONDING_TYPE);
1231 return nullptr;
1232 }
1233 }
1234
1235 auto promise = CommonFunc::AsyncCallNativeMethod(env, callbackPtr.get(), GetFunctionName(callbackPtr->option),
1236 UninstallOrRecoverExecuter, OperationCompleted);
1237 callbackPtr.release();
1238 return promise;
1239 }
1240
Recover(napi_env env, napi_callback_info info)1241 napi_value Recover(napi_env env, napi_callback_info info)
1242 {
1243 APP_LOGI("Recover called");
1244 std::unique_ptr<AsyncInstallCallbackInfo> callbackPtr = std::make_unique<AsyncInstallCallbackInfo>(env);
1245 callbackPtr->option = InstallOption::RECOVER;
1246 APP_LOGI("call Recover done");
1247 return UninstallOrRecover(env, info, callbackPtr);
1248 }
1249
Uninstall(napi_env env, napi_callback_info info)1250 napi_value Uninstall(napi_env env, napi_callback_info info)
1251 {
1252 APP_LOGI_NOFUNC("Uninstall called");
1253 std::unique_ptr<AsyncInstallCallbackInfo> callbackPtr = std::make_unique<AsyncInstallCallbackInfo>(env);
1254 callbackPtr->option = InstallOption::UNINSTALL;
1255 // uninstall uninstallParam
1256 NapiArg args(env, info);
1257 args.Init(ARGS_SIZE_ONE, ARGS_SIZE_THREE);
1258 napi_valuetype firstType = napi_undefined;
1259 napi_typeof(env, args[FIRST_PARAM], &firstType);
1260 if (firstType == napi_object) {
1261 return UninstallByUninstallParam(env, info, callbackPtr);
1262 }
1263 APP_LOGI_NOFUNC("call Uninstall done");
1264 return UninstallOrRecover(env, info, callbackPtr);
1265 }
1266
BundleInstallerConstructor(napi_env env, napi_callback_info info)1267 napi_value BundleInstallerConstructor(napi_env env, napi_callback_info info)
1268 {
1269 napi_value jsthis = nullptr;
1270 NAPI_CALL(env, napi_get_cb_info(env, info, nullptr, nullptr, &jsthis, nullptr));
1271 return jsthis;
1272 }
1273
1274 /**
1275 * Promise and async callback
1276 */
UpdateBundleForSelf(napi_env env, napi_callback_info info)1277 napi_value UpdateBundleForSelf(napi_env env, napi_callback_info info)
1278 {
1279 APP_LOGI("UpdateBundleForSelf called");
1280 // obtain arguments of install interface
1281 NapiArg args(env, info);
1282 if (!args.Init(ARGS_SIZE_TWO, ARGS_SIZE_THREE)) {
1283 APP_LOGE("init param failed");
1284 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1285 return nullptr;
1286 }
1287 auto argc = args.GetMaxArgc();
1288 std::unique_ptr<AsyncInstallCallbackInfo> callbackPtr = std::make_unique<AsyncInstallCallbackInfo>(env);
1289 callbackPtr->option = InstallOption::UPDATE_BUNDLE_FOR_SELF;
1290 for (size_t i = 0; i < argc; ++i) {
1291 napi_valuetype valueType = napi_undefined;
1292 napi_typeof(env, args[i], &valueType);
1293 if (i == ARGS_POS_ZERO) {
1294 if (!CommonFunc::ParseStringArray(env, callbackPtr->hapFiles, args[i])) {
1295 APP_LOGE("Flags %{public}s invalid", callbackPtr->bundleName.c_str());
1296 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, PARAMETERS, CORRESPONDING_TYPE);
1297 return nullptr;
1298 }
1299 } else if (i == ARGS_POS_ONE) {
1300 if (valueType == napi_function) {
1301 NAPI_CALL(env, napi_create_reference(env, args[i], NAPI_RETURN_ONE, &callbackPtr->callback));
1302 break;
1303 }
1304 if (valueType == napi_object && !ParseInstallParam(env, args[i], callbackPtr->installParam)) {
1305 APP_LOGE("Parse installParam failed");
1306 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, PARAMETERS, CORRESPONDING_TYPE);
1307 return nullptr;
1308 }
1309 } else if (i == ARGS_POS_TWO) {
1310 if (valueType == napi_function) {
1311 NAPI_CALL(env, napi_create_reference(env, args[i], NAPI_RETURN_ONE, &callbackPtr->callback));
1312 break;
1313 }
1314 } else {
1315 APP_LOGE("param check error");
1316 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, PARAMETERS, CORRESPONDING_TYPE);
1317 return nullptr;
1318 }
1319 }
1320 if (!CheckInstallParam(env, callbackPtr->installParam)) {
1321 return nullptr;
1322 }
1323 if (callbackPtr->hapFiles.empty() && !callbackPtr->installParam.verifyCodeParams.empty()) {
1324 BusinessError::ThrowError(env, ERROR_PARAM_CHECK_ERROR, HAPS_FILE_NEEDED);
1325 return nullptr;
1326 }
1327 callbackPtr->installParam.isSelfUpdate = true;
1328 auto promise = CommonFunc::AsyncCallNativeMethod(env, callbackPtr.get(), RESOURCE_NAME_OF_INSTALL, InstallExecuter,
1329 OperationCompleted);
1330 callbackPtr.release();
1331 APP_LOGI("call UpdateBundleForSelf done");
1332 return promise;
1333 }
1334
UninstallAndRecoverExecuter(napi_env env, void *data)1335 void UninstallAndRecoverExecuter(napi_env env, void *data)
1336 {
1337 AsyncInstallCallbackInfo *asyncCallbackInfo = reinterpret_cast<AsyncInstallCallbackInfo *>(data);
1338 if (asyncCallbackInfo == nullptr) {
1339 APP_LOGE("asyncCallbackInfo is nullptr");
1340 return;
1341 }
1342 const std::string bundleName = asyncCallbackInfo->bundleName;
1343 InstallResult &installResult = asyncCallbackInfo->installResult;
1344 if (bundleName.empty()) {
1345 installResult.resultCode = static_cast<int32_t>(IStatusReceiver::ERR_RECOVER_INVALID_BUNDLE_NAME);
1346 return;
1347 }
1348 auto iBundleInstaller = CommonFunc::GetBundleInstaller();
1349 if ((iBundleInstaller == nullptr) || (iBundleInstaller->AsObject() == nullptr)) {
1350 APP_LOGE("can not get iBundleInstaller");
1351 installResult.resultCode = static_cast<int32_t>(IStatusReceiver::ERR_INSTALL_INTERNAL_ERROR);
1352 return;
1353 }
1354 sptr<InstallerCallback> callback = new (std::nothrow) InstallerCallback();
1355 sptr<BundleDeathRecipient> recipient(new (std::nothrow) BundleDeathRecipient(callback));
1356 if (callback == nullptr || recipient == nullptr) {
1357 APP_LOGE("callback or death recipient is nullptr");
1358 installResult.resultCode = static_cast<int32_t>(IStatusReceiver::ERR_INSTALL_INTERNAL_ERROR);
1359 return;
1360 }
1361 iBundleInstaller->AsObject()->AddDeathRecipient(recipient);
1362 iBundleInstaller->UninstallAndRecover(bundleName, asyncCallbackInfo->installParam, callback);
1363 installResult.resultMsg = callback->GetResultMsg();
1364 installResult.resultCode = callback->GetResultCode();
1365 }
1366
UninstallAndRecover(napi_env env, napi_callback_info info)1367 napi_value UninstallAndRecover(napi_env env, napi_callback_info info)
1368 {
1369 APP_LOGI("UninstallAndRecover called");
1370 NapiArg args(env, info);
1371 if (!args.Init(ARGS_SIZE_ONE, ARGS_SIZE_TWO)) {
1372 APP_LOGE("init param failed");
1373 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1374 return nullptr;
1375 }
1376 std::unique_ptr<AsyncInstallCallbackInfo> callbackPtr = std::make_unique<AsyncInstallCallbackInfo>(env);
1377 callbackPtr->option = InstallOption::UNINSTALL_AND_RECOVER;
1378 for (size_t i = 0; i < args.GetArgc(); ++i) {
1379 napi_valuetype valueType = napi_undefined;
1380 napi_typeof(env, args[i], &valueType);
1381 if (i == ARGS_POS_ZERO) {
1382 if (!CommonFunc::ParseString(env, args[i], callbackPtr->bundleName)) {
1383 APP_LOGE("bundleName %{public}s invalid!", callbackPtr->bundleName.c_str());
1384 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, BUNDLE_NAME, TYPE_STRING);
1385 return nullptr;
1386 }
1387 } else if (i == ARGS_POS_ONE) {
1388 if (valueType != napi_object || !ParseInstallParam(env, args[i], callbackPtr->installParam)) {
1389 APP_LOGW("Parse installParam failed");
1390 }
1391 } else {
1392 APP_LOGE("The number of parameters is incorrect.");
1393 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1394 return nullptr;
1395 }
1396 }
1397 auto promise = CommonFunc::AsyncCallNativeMethod(env, callbackPtr.get(), RESOURCE_NAME_OF_UNINSTALL_AND_RECOVER,
1398 UninstallAndRecoverExecuter, OperationCompleted);
1399 callbackPtr.release();
1400 APP_LOGI("call UninstallAndRecover done");
1401 return promise;
1402 }
1403
InnerAddExtResource( const std::string &bundleName, const std::vector<std::string> &filePaths)1404 ErrCode InnerAddExtResource(
1405 const std::string &bundleName, const std::vector<std::string> &filePaths)
1406 {
1407 auto extResourceManager = CommonFunc::GetExtendResourceManager();
1408 if (extResourceManager == nullptr) {
1409 APP_LOGE("extResourceManager is null");
1410 return ERROR_BUNDLE_SERVICE_EXCEPTION;
1411 }
1412
1413 std::vector<std::string> destFiles;
1414 ErrCode ret = extResourceManager->CopyFiles(filePaths, destFiles);
1415 if (ret != ERR_OK) {
1416 APP_LOGE("CopyFiles failed");
1417 return CommonFunc::ConvertErrCode(ret);
1418 }
1419
1420 ret = extResourceManager->AddExtResource(bundleName, destFiles);
1421 if (ret != ERR_OK) {
1422 APP_LOGE("AddExtResource failed");
1423 }
1424
1425 return CommonFunc::ConvertErrCode(ret);
1426 }
1427
AddExtResourceExec(napi_env env, void *data)1428 void AddExtResourceExec(napi_env env, void *data)
1429 {
1430 ExtResourceCallbackInfo *asyncCallbackInfo = reinterpret_cast<ExtResourceCallbackInfo *>(data);
1431 if (asyncCallbackInfo == nullptr) {
1432 APP_LOGE("asyncCallbackInfo is null");
1433 return;
1434 }
1435 asyncCallbackInfo->err = InnerAddExtResource(
1436 asyncCallbackInfo->bundleName, asyncCallbackInfo->filePaths);
1437 }
1438
AddExtResourceComplete(napi_env env, napi_status status, void *data)1439 void AddExtResourceComplete(napi_env env, napi_status status, void *data)
1440 {
1441 ExtResourceCallbackInfo *asyncCallbackInfo = reinterpret_cast<ExtResourceCallbackInfo *>(data);
1442 if (asyncCallbackInfo == nullptr) {
1443 APP_LOGE("asyncCallbackInfo is null");
1444 return;
1445 }
1446
1447 std::unique_ptr<ExtResourceCallbackInfo> callbackPtr {asyncCallbackInfo};
1448 napi_value result[ARGS_POS_TWO] = {0};
1449 if (asyncCallbackInfo->err == NO_ERROR) {
1450 NAPI_CALL_RETURN_VOID(env, napi_get_null(env, &result[0]));
1451 } else {
1452 result[0] = BusinessError::CreateCommonError(
1453 env, asyncCallbackInfo->err, ADD_EXT_RESOURCE, Constants::PERMISSION_INSTALL_BUNDLE);
1454 }
1455
1456 CommonFunc::NapiReturnDeferred<ExtResourceCallbackInfo>(
1457 env, asyncCallbackInfo, result, ARGS_SIZE_ONE);
1458 }
1459
AddExtResource(napi_env env, napi_callback_info info)1460 napi_value AddExtResource(napi_env env, napi_callback_info info)
1461 {
1462 APP_LOGD("AddExtResource called");
1463 NapiArg args(env, info);
1464 ExtResourceCallbackInfo *asyncCallbackInfo = new (std::nothrow) ExtResourceCallbackInfo(env);
1465 if (asyncCallbackInfo == nullptr) {
1466 APP_LOGE("asyncCallbackInfo is null");
1467 return nullptr;
1468 }
1469 std::unique_ptr<ExtResourceCallbackInfo> callbackPtr {asyncCallbackInfo};
1470 if (!args.Init(ARGS_SIZE_TWO, ARGS_SIZE_TWO)) {
1471 APP_LOGE("param count invalid");
1472 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1473 return nullptr;
1474 }
1475 for (size_t i = 0; i < args.GetArgc(); ++i) {
1476 napi_valuetype valueType = napi_undefined;
1477 napi_typeof(env, args[i], &valueType);
1478 if (i == ARGS_POS_ZERO) {
1479 if (!CommonFunc::ParseString(env, args[i], asyncCallbackInfo->bundleName)) {
1480 APP_LOGE("bundleName invalid");
1481 BusinessError::ThrowParameterTypeError(
1482 env, ERROR_PARAM_CHECK_ERROR, BUNDLE_NAME, TYPE_STRING);
1483 return nullptr;
1484 }
1485 } else if (i == ARGS_POS_ONE) {
1486 if (CommonFunc::ParseStringArray(env, asyncCallbackInfo->filePaths, args[i]) == nullptr) {
1487 APP_LOGE("filePaths invalid");
1488 BusinessError::ThrowParameterTypeError(
1489 env, ERROR_PARAM_CHECK_ERROR, FILE_PATH, TYPE_ARRAY);
1490 return nullptr;
1491 }
1492 }
1493 }
1494 auto promise = CommonFunc::AsyncCallNativeMethod<ExtResourceCallbackInfo>(
1495 env, asyncCallbackInfo, "AddExtResource", AddExtResourceExec, AddExtResourceComplete);
1496 callbackPtr.release();
1497 APP_LOGD("call AddExtResource done");
1498 return promise;
1499 }
1500
InnerRemoveExtResource( const std::string &bundleName, const std::vector<std::string> &moduleNames)1501 ErrCode InnerRemoveExtResource(
1502 const std::string &bundleName, const std::vector<std::string> &moduleNames)
1503 {
1504 auto extResourceManager = CommonFunc::GetExtendResourceManager();
1505 if (extResourceManager == nullptr) {
1506 APP_LOGE("extResourceManager is null");
1507 return ERROR_BUNDLE_SERVICE_EXCEPTION;
1508 }
1509
1510 ErrCode ret = extResourceManager->RemoveExtResource(bundleName, moduleNames);
1511 if (ret != ERR_OK) {
1512 APP_LOGE("RemoveExtResource failed");
1513 }
1514
1515 return CommonFunc::ConvertErrCode(ret);
1516 }
1517
RemoveExtResourceExec(napi_env env, void *data)1518 void RemoveExtResourceExec(napi_env env, void *data)
1519 {
1520 ExtResourceCallbackInfo *asyncCallbackInfo = reinterpret_cast<ExtResourceCallbackInfo *>(data);
1521 if (asyncCallbackInfo == nullptr) {
1522 APP_LOGE("asyncCallbackInfo is null");
1523 return;
1524 }
1525 asyncCallbackInfo->err = InnerRemoveExtResource(
1526 asyncCallbackInfo->bundleName, asyncCallbackInfo->moduleNames);
1527 }
1528
RemoveExtResourceComplete(napi_env env, napi_status status, void *data)1529 void RemoveExtResourceComplete(napi_env env, napi_status status, void *data)
1530 {
1531 ExtResourceCallbackInfo *asyncCallbackInfo = reinterpret_cast<ExtResourceCallbackInfo *>(data);
1532 if (asyncCallbackInfo == nullptr) {
1533 APP_LOGE("asyncCallbackInfo is null");
1534 return;
1535 }
1536
1537 std::unique_ptr<ExtResourceCallbackInfo> callbackPtr {asyncCallbackInfo};
1538 napi_value result[ARGS_POS_TWO] = {0};
1539 if (asyncCallbackInfo->err == NO_ERROR) {
1540 NAPI_CALL_RETURN_VOID(env, napi_get_null(env, &result[0]));
1541 } else {
1542 result[0] = BusinessError::CreateCommonError(
1543 env, asyncCallbackInfo->err, REMOVE_EXT_RESOURCE, Constants::PERMISSION_INSTALL_BUNDLE);
1544 }
1545
1546 CommonFunc::NapiReturnDeferred<ExtResourceCallbackInfo>(
1547 env, asyncCallbackInfo, result, ARGS_SIZE_ONE);
1548 }
1549
RemoveExtResource(napi_env env, napi_callback_info info)1550 napi_value RemoveExtResource(napi_env env, napi_callback_info info)
1551 {
1552 APP_LOGD("RemoveExtResource called");
1553 NapiArg args(env, info);
1554 ExtResourceCallbackInfo *asyncCallbackInfo = new (std::nothrow) ExtResourceCallbackInfo(env);
1555 if (asyncCallbackInfo == nullptr) {
1556 APP_LOGE("asyncCallbackInfo is null");
1557 return nullptr;
1558 }
1559 std::unique_ptr<ExtResourceCallbackInfo> callbackPtr {asyncCallbackInfo};
1560 if (!args.Init(ARGS_SIZE_TWO, ARGS_SIZE_TWO)) {
1561 APP_LOGE("param count invalid");
1562 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1563 return nullptr;
1564 }
1565 for (size_t i = 0; i < args.GetArgc(); ++i) {
1566 napi_valuetype valueType = napi_undefined;
1567 napi_typeof(env, args[i], &valueType);
1568 if (i == ARGS_POS_ZERO) {
1569 if (!CommonFunc::ParseString(env, args[i], asyncCallbackInfo->bundleName)) {
1570 APP_LOGE("bundleName invalid");
1571 BusinessError::ThrowParameterTypeError(
1572 env, ERROR_PARAM_CHECK_ERROR, BUNDLE_NAME, TYPE_STRING);
1573 return nullptr;
1574 }
1575 } else if (i == ARGS_POS_ONE) {
1576 if (CommonFunc::ParseStringArray(env, asyncCallbackInfo->moduleNames, args[i]) == nullptr) {
1577 APP_LOGE("moduleNames invalid");
1578 BusinessError::ThrowParameterTypeError(
1579 env, ERROR_PARAM_CHECK_ERROR, MODULE_NAME, TYPE_ARRAY);
1580 return nullptr;
1581 }
1582 }
1583 }
1584 auto promise = CommonFunc::AsyncCallNativeMethod<ExtResourceCallbackInfo>(
1585 env, asyncCallbackInfo, "RemoveExtResource", RemoveExtResourceExec, RemoveExtResourceComplete);
1586 callbackPtr.release();
1587 APP_LOGD("call RemoveExtResource done");
1588 return promise;
1589 }
1590
InnerCreateAppClone(std::string &bundleName, int32_t userId, int32_t &appIndex)1591 static ErrCode InnerCreateAppClone(std::string &bundleName, int32_t userId, int32_t &appIndex)
1592 {
1593 auto iBundleMgr = CommonFunc::GetBundleMgr();
1594 if (iBundleMgr == nullptr) {
1595 APP_LOGE("can not get iBundleMgr");
1596 return ERROR_BUNDLE_SERVICE_EXCEPTION;
1597 }
1598 auto iBundleInstaller = iBundleMgr->GetBundleInstaller();
1599 if ((iBundleInstaller == nullptr) || (iBundleInstaller->AsObject() == nullptr)) {
1600 APP_LOGE("can not get iBundleInstaller");
1601 return ERROR_BUNDLE_SERVICE_EXCEPTION;
1602 }
1603 ErrCode result = iBundleInstaller->InstallCloneApp(bundleName, userId, appIndex);
1604 APP_LOGD("InstallCloneApp result is %{public}d", result);
1605 return result;
1606 }
1607
CreateAppCloneExec(napi_env env, void *data)1608 void CreateAppCloneExec(napi_env env, void *data)
1609 {
1610 CreateAppCloneCallbackInfo *asyncCallbackInfo = reinterpret_cast<CreateAppCloneCallbackInfo *>(data);
1611 if (asyncCallbackInfo == nullptr) {
1612 APP_LOGE("asyncCallbackInfo is null");
1613 return;
1614 }
1615 APP_LOGD("CreateAppCloneExec param: bundleName = %{public}s, userId = %{public}d, appIndex = %{public}d",
1616 asyncCallbackInfo->bundleName.c_str(),
1617 asyncCallbackInfo->userId,
1618 asyncCallbackInfo->appIndex);
1619 asyncCallbackInfo->err =
1620 InnerCreateAppClone(asyncCallbackInfo->bundleName, asyncCallbackInfo->userId, asyncCallbackInfo->appIndex);
1621 }
1622
CreateAppCloneComplete(napi_env env, napi_status status, void *data)1623 void CreateAppCloneComplete(napi_env env, napi_status status, void *data)
1624 {
1625 CreateAppCloneCallbackInfo *asyncCallbackInfo = reinterpret_cast<CreateAppCloneCallbackInfo *>(data);
1626 if (asyncCallbackInfo == nullptr) {
1627 APP_LOGE("asyncCallbackInfo is null");
1628 return;
1629 }
1630 std::unique_ptr<CreateAppCloneCallbackInfo> callbackPtr {asyncCallbackInfo};
1631 asyncCallbackInfo->err = CommonFunc::ConvertErrCode(asyncCallbackInfo->err);
1632 APP_LOGD("CreateAppCloneComplete err is %{public}d, appIndex is %{public}d",
1633 asyncCallbackInfo->err,
1634 asyncCallbackInfo->appIndex);
1635 napi_value result[ARGS_SIZE_TWO] = {0};
1636 if (asyncCallbackInfo->err == SUCCESS) {
1637 NAPI_CALL_RETURN_VOID(env, napi_get_null(env, &result[FIRST_PARAM]));
1638 NAPI_CALL_RETURN_VOID(env, napi_create_int32(env, asyncCallbackInfo->appIndex, &result[SECOND_PARAM]));
1639 } else {
1640 result[FIRST_PARAM] = BusinessError::CreateCommonError(env, asyncCallbackInfo->err,
1641 CREATE_APP_CLONE, Constants::PERMISSION_INSTALL_CLONE_BUNDLE);
1642 }
1643 CommonFunc::NapiReturnDeferred<CreateAppCloneCallbackInfo>(env, asyncCallbackInfo, result, ARGS_SIZE_TWO);
1644 }
1645
ParseAppCloneParam(napi_env env, napi_value args, int32_t &userId, int32_t &appIndex)1646 void ParseAppCloneParam(napi_env env, napi_value args, int32_t &userId, int32_t &appIndex)
1647 {
1648 if (!ParseUserId(env, args, userId)) {
1649 APP_LOGI("parse userId failed. assign a default value = %{public}d", userId);
1650 }
1651 if (ParseAppIndex(env, args, appIndex)) {
1652 if (appIndex == 0) {
1653 APP_LOGI("parse appIndex success, but appIndex is 0, assign a value: %{public}d", ILLEGAL_APP_INDEX);
1654 appIndex = ILLEGAL_APP_INDEX;
1655 }
1656 } else {
1657 APP_LOGI("parse appIndex failed. assign a default value = %{public}d", appIndex);
1658 }
1659 }
1660
CreateAppClone(napi_env env, napi_callback_info info)1661 napi_value CreateAppClone(napi_env env, napi_callback_info info)
1662 {
1663 APP_LOGI("begin to CreateAppClone");
1664 NapiArg args(env, info);
1665 std::unique_ptr<CreateAppCloneCallbackInfo> asyncCallbackInfo = std::make_unique<CreateAppCloneCallbackInfo>(env);
1666 if (asyncCallbackInfo == nullptr) {
1667 APP_LOGW("asyncCallbackInfo is null");
1668 return nullptr;
1669 }
1670 if (!args.Init(ARGS_SIZE_ONE, ARGS_SIZE_TWO)) {
1671 APP_LOGW("param count invalid");
1672 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1673 return nullptr;
1674 }
1675 size_t argc = args.GetMaxArgc();
1676 for (size_t i = 0; i < argc; ++i) {
1677 napi_valuetype valueType = napi_undefined;
1678 napi_typeof(env, args[i], &valueType);
1679 if (i == ARGS_POS_ZERO) {
1680 if (!CommonFunc::ParseString(env, args[i], asyncCallbackInfo->bundleName)) {
1681 APP_LOGW("parse bundleName failed");
1682 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, BUNDLE_NAME, TYPE_STRING);
1683 return nullptr;
1684 }
1685 } else if (i == ARGS_POS_ONE) {
1686 if (valueType == napi_object) {
1687 ParseAppCloneParam(env, args[i], asyncCallbackInfo->userId, asyncCallbackInfo->appIndex);
1688 }
1689 } else {
1690 APP_LOGW("The number of parameters is incorrect");
1691 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1692 return nullptr;
1693 }
1694 }
1695 if (asyncCallbackInfo->userId == Constants::UNSPECIFIED_USERID) {
1696 asyncCallbackInfo->userId = IPCSkeleton::GetCallingUid() / Constants::BASE_USER_RANGE;
1697 }
1698 auto promise = CommonFunc::AsyncCallNativeMethod<CreateAppCloneCallbackInfo>(
1699 env, asyncCallbackInfo.get(), CREATE_APP_CLONE, CreateAppCloneExec, CreateAppCloneComplete);
1700 asyncCallbackInfo.release();
1701 APP_LOGI("call napi CreateAppClone done");
1702 return promise;
1703 }
1704
InnerDestroyAppClone(std::string &bundleName, int32_t userId, int32_t appIndex)1705 static ErrCode InnerDestroyAppClone(std::string &bundleName, int32_t userId, int32_t appIndex)
1706 {
1707 auto iBundleMgr = CommonFunc::GetBundleMgr();
1708 if (iBundleMgr == nullptr) {
1709 APP_LOGE("can not get iBundleMgr");
1710 return ERROR_BUNDLE_SERVICE_EXCEPTION;
1711 }
1712 auto iBundleInstaller = iBundleMgr->GetBundleInstaller();
1713 if ((iBundleInstaller == nullptr) || (iBundleInstaller->AsObject() == nullptr)) {
1714 APP_LOGE("can not get iBundleInstaller");
1715 return ERROR_BUNDLE_SERVICE_EXCEPTION;
1716 }
1717 ErrCode result = iBundleInstaller->UninstallCloneApp(bundleName, userId, appIndex);
1718 APP_LOGD("UninstallCloneApp result is %{public}d", result);
1719 return result;
1720 }
1721
DestroyAppCloneExec(napi_env env, void *data)1722 void DestroyAppCloneExec(napi_env env, void *data)
1723 {
1724 CreateAppCloneCallbackInfo *asyncCallbackInfo = reinterpret_cast<CreateAppCloneCallbackInfo *>(data);
1725 if (asyncCallbackInfo == nullptr) {
1726 APP_LOGE("asyncCallbackInfo is null");
1727 return;
1728 }
1729 APP_LOGD("DestroyAppCloneExec param: bundleName = %{public}s, userId = %{public}d, appIndex = %{public}d",
1730 asyncCallbackInfo->bundleName.c_str(),
1731 asyncCallbackInfo->userId,
1732 asyncCallbackInfo->appIndex);
1733 asyncCallbackInfo->err =
1734 InnerDestroyAppClone(asyncCallbackInfo->bundleName, asyncCallbackInfo->userId, asyncCallbackInfo->appIndex);
1735 }
1736
DestroyAppCloneComplete(napi_env env, napi_status status, void *data)1737 void DestroyAppCloneComplete(napi_env env, napi_status status, void *data)
1738 {
1739 CreateAppCloneCallbackInfo *asyncCallbackInfo = reinterpret_cast<CreateAppCloneCallbackInfo *>(data);
1740 if (asyncCallbackInfo == nullptr) {
1741 APP_LOGE("asyncCallbackInfo is null");
1742 return;
1743 }
1744 std::unique_ptr<CreateAppCloneCallbackInfo> callbackPtr {asyncCallbackInfo};
1745 asyncCallbackInfo->err = CommonFunc::ConvertErrCode(asyncCallbackInfo->err);
1746 APP_LOGD("DestroyAppCloneComplete err is %{public}d, appIndex is %{public}d",
1747 asyncCallbackInfo->err,
1748 asyncCallbackInfo->appIndex);
1749 napi_value result[ARGS_SIZE_TWO] = {0};
1750 if (asyncCallbackInfo->err == SUCCESS) {
1751 NAPI_CALL_RETURN_VOID(env, napi_get_null(env, &result[FIRST_PARAM]));
1752 } else {
1753 result[FIRST_PARAM] = BusinessError::CreateCommonError(env, asyncCallbackInfo->err,
1754 DESTROY_APP_CLONE, Constants::PERMISSION_UNINSTALL_CLONE_BUNDLE);
1755 }
1756 CommonFunc::NapiReturnDeferred<CreateAppCloneCallbackInfo>(env, asyncCallbackInfo, result, ARGS_SIZE_ONE);
1757 }
1758
DestroyAppClone(napi_env env, napi_callback_info info)1759 napi_value DestroyAppClone(napi_env env, napi_callback_info info)
1760 {
1761 APP_LOGI("begin to destroyAppClone");
1762 NapiArg args(env, info);
1763 std::unique_ptr<CreateAppCloneCallbackInfo> asyncCallbackInfo = std::make_unique<CreateAppCloneCallbackInfo>(env);
1764 if (asyncCallbackInfo == nullptr) {
1765 APP_LOGW("asyncCallbackInfo is null");
1766 return nullptr;
1767 }
1768 if (!args.Init(ARGS_SIZE_TWO, ARGS_SIZE_THREE)) {
1769 APP_LOGW("param count invalid");
1770 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1771 return nullptr;
1772 }
1773 size_t argc = args.GetMaxArgc();
1774 for (size_t i = 0; i < argc; ++i) {
1775 napi_valuetype valueType = napi_undefined;
1776 napi_typeof(env, args[i], &valueType);
1777 if (i == ARGS_POS_ZERO) {
1778 if (!CommonFunc::ParseString(env, args[i], asyncCallbackInfo->bundleName)) {
1779 APP_LOGW("parse bundleName failed");
1780 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, BUNDLE_NAME, TYPE_STRING);
1781 return nullptr;
1782 }
1783 } else if (i == ARGS_POS_ONE) {
1784 if (!CommonFunc::ParseInt(env, args[i], asyncCallbackInfo->appIndex)) {
1785 APP_LOGW("parse appIndex failed");
1786 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, APP_INDEX, TYPE_NUMBER);
1787 return nullptr;
1788 }
1789 } else if (i == ARGS_POS_TWO) {
1790 if (!CommonFunc::ParseInt(env, args[i], asyncCallbackInfo->userId)) {
1791 APP_LOGW("Parse userId failed, set this parameter to the caller userId");
1792 }
1793 } else {
1794 APP_LOGE("The number of parameters is incorrect");
1795 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1796 return nullptr;
1797 }
1798 }
1799 if (asyncCallbackInfo->userId == Constants::UNSPECIFIED_USERID) {
1800 asyncCallbackInfo->userId = IPCSkeleton::GetCallingUid() / Constants::BASE_USER_RANGE;
1801 }
1802 auto promise = CommonFunc::AsyncCallNativeMethod<CreateAppCloneCallbackInfo>(
1803 env, asyncCallbackInfo.get(), DESTROY_APP_CLONE, DestroyAppCloneExec, DestroyAppCloneComplete);
1804 asyncCallbackInfo.release();
1805 APP_LOGI("call napi destroyAppTwin done");
1806 return promise;
1807 }
1808
InnerInstallPreexistingApp(std::string &bundleName, int32_t userId)1809 static ErrCode InnerInstallPreexistingApp(std::string &bundleName, int32_t userId)
1810 {
1811 auto iBundleMgr = CommonFunc::GetBundleMgr();
1812 if (iBundleMgr == nullptr) {
1813 APP_LOGE("can not get iBundleMgr");
1814 return ERROR_BUNDLE_SERVICE_EXCEPTION;
1815 }
1816 auto iBundleInstaller = iBundleMgr->GetBundleInstaller();
1817 if ((iBundleInstaller == nullptr) || (iBundleInstaller->AsObject() == nullptr)) {
1818 APP_LOGE("can not get iBundleInstaller");
1819 return ERROR_BUNDLE_SERVICE_EXCEPTION;
1820 }
1821 ErrCode result = iBundleInstaller->InstallExisted(bundleName, userId);
1822 APP_LOGD("result is %{public}d", result);
1823 return result;
1824 }
1825
InstallPreexistingAppExec(napi_env env, void *data)1826 void InstallPreexistingAppExec(napi_env env, void *data)
1827 {
1828 InstallPreexistingAppCallbackInfo *asyncCallbackInfo = reinterpret_cast<InstallPreexistingAppCallbackInfo *>(data);
1829 if (asyncCallbackInfo == nullptr) {
1830 APP_LOGE("asyncCallbackInfo is null");
1831 return;
1832 }
1833 APP_LOGD("param: bundleName = %{public}s, userId = %{public}d",
1834 asyncCallbackInfo->bundleName.c_str(),
1835 asyncCallbackInfo->userId);
1836 asyncCallbackInfo->err =
1837 InnerInstallPreexistingApp(asyncCallbackInfo->bundleName, asyncCallbackInfo->userId);
1838 }
1839
InstallPreexistingAppComplete(napi_env env, napi_status status, void *data)1840 void InstallPreexistingAppComplete(napi_env env, napi_status status, void *data)
1841 {
1842 InstallPreexistingAppCallbackInfo *asyncCallbackInfo = reinterpret_cast<InstallPreexistingAppCallbackInfo *>(data);
1843 if (asyncCallbackInfo == nullptr) {
1844 APP_LOGE("asyncCallbackInfo is null");
1845 return;
1846 }
1847 std::unique_ptr<InstallPreexistingAppCallbackInfo> callbackPtr {asyncCallbackInfo};
1848 asyncCallbackInfo->err = CommonFunc::ConvertErrCode(asyncCallbackInfo->err);
1849 APP_LOGD("err is %{public}d", asyncCallbackInfo->err);
1850
1851 napi_value result[ARGS_SIZE_ONE] = {0};
1852 if (asyncCallbackInfo->err == SUCCESS) {
1853 NAPI_CALL_RETURN_VOID(env, napi_get_null(env, &result[FIRST_PARAM]));
1854 } else {
1855 result[FIRST_PARAM] = BusinessError::CreateCommonError(env, asyncCallbackInfo->err,
1856 INSTALL_PREEXISTING_APP, Constants::PERMISSION_INSTALL_BUNDLE);
1857 }
1858 CommonFunc::NapiReturnDeferred<InstallPreexistingAppCallbackInfo>(env, asyncCallbackInfo, result, ARGS_SIZE_ONE);
1859 }
1860
InstallPreexistingApp(napi_env env, napi_callback_info info)1861 napi_value InstallPreexistingApp(napi_env env, napi_callback_info info)
1862 {
1863 APP_LOGI("begin");
1864 NapiArg args(env, info);
1865 std::unique_ptr<InstallPreexistingAppCallbackInfo> asyncCallbackInfo
1866 = std::make_unique<InstallPreexistingAppCallbackInfo>(env);
1867 if (asyncCallbackInfo == nullptr) {
1868 APP_LOGW("asyncCallbackInfo is null");
1869 return nullptr;
1870 }
1871 if (!args.Init(ARGS_SIZE_ONE, ARGS_SIZE_TWO)) {
1872 APP_LOGW("param count invalid");
1873 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1874 return nullptr;
1875 }
1876 size_t argc = args.GetMaxArgc();
1877 for (size_t i = 0; i < argc; ++i) {
1878 if (i == ARGS_POS_ZERO) {
1879 if (!CommonFunc::ParseString(env, args[i], asyncCallbackInfo->bundleName)) {
1880 APP_LOGW("parse bundleName failed");
1881 BusinessError::ThrowParameterTypeError(env, ERROR_PARAM_CHECK_ERROR, BUNDLE_NAME, TYPE_STRING);
1882 return nullptr;
1883 }
1884 } else if (i == ARGS_POS_ONE) {
1885 if (!CommonFunc::ParseInt(env, args[i], asyncCallbackInfo->userId)) {
1886 APP_LOGW("parse userId failed");
1887 }
1888 } else {
1889 APP_LOGW("The number of parameters is incorrect");
1890 BusinessError::ThrowTooFewParametersError(env, ERROR_PARAM_CHECK_ERROR);
1891 return nullptr;
1892 }
1893 }
1894 if (asyncCallbackInfo->userId == Constants::UNSPECIFIED_USERID) {
1895 asyncCallbackInfo->userId = IPCSkeleton::GetCallingUid() / Constants::BASE_USER_RANGE;
1896 }
1897 auto promise = CommonFunc::AsyncCallNativeMethod<InstallPreexistingAppCallbackInfo>(
1898 env, asyncCallbackInfo.get(), INSTALL_PREEXISTING_APP,
1899 InstallPreexistingAppExec, InstallPreexistingAppComplete);
1900 asyncCallbackInfo.release();
1901 APP_LOGI("call napi done");
1902 return promise;
1903 }
1904 } // AppExecFwk
1905 } // OHOS