122736c2fSopenharmony_ci/*
222736c2fSopenharmony_ci * Copyright (c) 2023 Huawei Device Co., Ltd.
322736c2fSopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License");
422736c2fSopenharmony_ci * you may not use this file except in compliance with the License.
522736c2fSopenharmony_ci * You may obtain a copy of the License at
622736c2fSopenharmony_ci *
722736c2fSopenharmony_ci *     http://www.apache.org/licenses/LICENSE-2.0
822736c2fSopenharmony_ci *
922736c2fSopenharmony_ci * Unless required by applicable law or agreed to in writing, software
1022736c2fSopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS,
1122736c2fSopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1222736c2fSopenharmony_ci * See the License for the specific language governing permissions and
1322736c2fSopenharmony_ci * limitations under the License.
1422736c2fSopenharmony_ci */
1522736c2fSopenharmony_ci
1622736c2fSopenharmony_ci#include "ime_info_inquirer.h"
1722736c2fSopenharmony_ci
1822736c2fSopenharmony_ci#include <algorithm>
1922736c2fSopenharmony_ci#include <string>
2022736c2fSopenharmony_ci
2122736c2fSopenharmony_ci#include "app_mgr_client.h"
2222736c2fSopenharmony_ci#include "application_info.h"
2322736c2fSopenharmony_ci#include "bundle_mgr_client_impl.h"
2422736c2fSopenharmony_ci#include "file_operator.h"
2522736c2fSopenharmony_ci#include "full_ime_info_manager.h"
2622736c2fSopenharmony_ci#include "global.h"
2722736c2fSopenharmony_ci#include "if_system_ability_manager.h"
2822736c2fSopenharmony_ci#include "ime_cfg_manager.h"
2922736c2fSopenharmony_ci#include "input_method_info.h"
3022736c2fSopenharmony_ci#include "input_type_manager.h"
3122736c2fSopenharmony_ci#include "iservice_registry.h"
3222736c2fSopenharmony_ci#include "locale_config.h"
3322736c2fSopenharmony_ci#include "locale_info.h"
3422736c2fSopenharmony_ci#include "os_account_adapter.h"
3522736c2fSopenharmony_ci#include "parameter.h"
3622736c2fSopenharmony_ci#include "running_process_info.h"
3722736c2fSopenharmony_ci#include "string_ex.h"
3822736c2fSopenharmony_ci#include "system_ability.h"
3922736c2fSopenharmony_ci#include "system_ability_definition.h"
4022736c2fSopenharmony_ci
4122736c2fSopenharmony_cinamespace OHOS {
4222736c2fSopenharmony_cinamespace MiscServices {
4322736c2fSopenharmony_cinamespace {
4422736c2fSopenharmony_ciusing namespace OHOS::AppExecFwk;
4522736c2fSopenharmony_ciusing namespace Global::Resource;
4622736c2fSopenharmony_ciusing namespace OHOS::AAFwk;
4722736c2fSopenharmony_ciconstexpr const char *SUBTYPE_PROFILE_METADATA_NAME = "ohos.extension.input_method";
4822736c2fSopenharmony_ciconstexpr const char *TEMPORARY_INPUT_METHOD_METADATA_NAME = "ohos.extension.temporary_input_method";
4922736c2fSopenharmony_ciconstexpr uint32_t SUBTYPE_PROFILE_NUM = 1;
5022736c2fSopenharmony_ciconstexpr const char *DEFAULT_IME_KEY = "persist.sys.default_ime";
5122736c2fSopenharmony_ciconstexpr int32_t CONFIG_LEN = 128;
5222736c2fSopenharmony_ciconstexpr uint32_t DEFAULT_BMS_VALUE = 0;
5322736c2fSopenharmony_ci} // namespace
5422736c2fSopenharmony_ciImeInfoInquirer &ImeInfoInquirer::GetInstance()
5522736c2fSopenharmony_ci{
5622736c2fSopenharmony_ci    static ImeInfoInquirer instance;
5722736c2fSopenharmony_ci    return instance;
5822736c2fSopenharmony_ci}
5922736c2fSopenharmony_ci
6022736c2fSopenharmony_civoid ImeInfoInquirer::InitSystemConfig()
6122736c2fSopenharmony_ci{
6222736c2fSopenharmony_ci    auto ret = SysCfgParser::ParseSystemConfig(systemConfig_);
6322736c2fSopenharmony_ci    if (!ret) {
6422736c2fSopenharmony_ci        IMSA_HILOGE("parse systemConfig failed!");
6522736c2fSopenharmony_ci        return;
6622736c2fSopenharmony_ci    }
6722736c2fSopenharmony_ci}
6822736c2fSopenharmony_ci
6922736c2fSopenharmony_cibool ImeInfoInquirer::IsEnableInputMethod()
7022736c2fSopenharmony_ci{
7122736c2fSopenharmony_ci    return systemConfig_.enableInputMethodFeature;
7222736c2fSopenharmony_ci}
7322736c2fSopenharmony_ci
7422736c2fSopenharmony_cibool ImeInfoInquirer::IsEnableSecurityMode()
7522736c2fSopenharmony_ci{
7622736c2fSopenharmony_ci    return systemConfig_.enableFullExperienceFeature;
7722736c2fSopenharmony_ci}
7822736c2fSopenharmony_ci
7922736c2fSopenharmony_cibool ImeInfoInquirer::QueryImeExtInfos(const int32_t userId, std::vector<ExtensionAbilityInfo> &infos)
8022736c2fSopenharmony_ci{
8122736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d.", userId);
8222736c2fSopenharmony_ci    auto bundleMgr = GetBundleMgr();
8322736c2fSopenharmony_ci    if (bundleMgr == nullptr) {
8422736c2fSopenharmony_ci        IMSA_HILOGE("failed to GetBundleMgr!");
8522736c2fSopenharmony_ci        return false;
8622736c2fSopenharmony_ci    }
8722736c2fSopenharmony_ci    if (!bundleMgr->QueryExtensionAbilityInfos(ExtensionAbilityType::INPUTMETHOD, userId, infos)) {
8822736c2fSopenharmony_ci        IMSA_HILOGF("query extension infos failed from bundleMgr!");
8922736c2fSopenharmony_ci        return false;
9022736c2fSopenharmony_ci    }
9122736c2fSopenharmony_ci    return true;
9222736c2fSopenharmony_ci}
9322736c2fSopenharmony_ci
9422736c2fSopenharmony_ciint32_t ImeInfoInquirer::GetExtInfosByBundleName(const int32_t userId, const std::string &bundleName,
9522736c2fSopenharmony_ci    std::vector<AppExecFwk::ExtensionAbilityInfo> &extInfos)
9622736c2fSopenharmony_ci{
9722736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d, bundleName: %{public}s.", userId, bundleName.c_str());
9822736c2fSopenharmony_ci    std::vector<AppExecFwk::ExtensionAbilityInfo> tempExtInfos;
9922736c2fSopenharmony_ci    if (!QueryImeExtInfos(userId, tempExtInfos)) {
10022736c2fSopenharmony_ci        IMSA_HILOGE("failed to QueryImeExtInfos!");
10122736c2fSopenharmony_ci        return ErrorCode::ERROR_BAD_PARAMETERS;
10222736c2fSopenharmony_ci    }
10322736c2fSopenharmony_ci    for (const auto &extInfo : tempExtInfos) {
10422736c2fSopenharmony_ci        if (extInfo.bundleName == bundleName) {
10522736c2fSopenharmony_ci            extInfos.emplace_back(extInfo);
10622736c2fSopenharmony_ci        }
10722736c2fSopenharmony_ci    }
10822736c2fSopenharmony_ci    if (extInfos.empty()) {
10922736c2fSopenharmony_ci        IMSA_HILOGE("bundleName: %{public}s extInfos is empty!", bundleName.c_str());
11022736c2fSopenharmony_ci        return ErrorCode::ERROR_BAD_PARAMETERS;
11122736c2fSopenharmony_ci    }
11222736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
11322736c2fSopenharmony_ci}
11422736c2fSopenharmony_ci
11522736c2fSopenharmony_cistd::shared_ptr<ImeInfo> ImeInfoInquirer::GetImeInfo(int32_t userId, const std::string &bundleName,
11622736c2fSopenharmony_ci    const std::string &subName)
11722736c2fSopenharmony_ci{
11822736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d, bundleName: %{public}s, subName: %{public}s.", userId, bundleName.c_str(),
11922736c2fSopenharmony_ci        subName.c_str());
12022736c2fSopenharmony_ci    auto info = GetImeInfoFromCache(userId, bundleName, subName);
12122736c2fSopenharmony_ci    return info == nullptr ? GetImeInfoFromBundleMgr(userId, bundleName, subName) : info;
12222736c2fSopenharmony_ci}
12322736c2fSopenharmony_ci
12422736c2fSopenharmony_cistd::shared_ptr<ImeInfo> ImeInfoInquirer::GetImeInfoFromCache(const int32_t userId, const std::string &bundleName,
12522736c2fSopenharmony_ci    const std::string &subName)
12622736c2fSopenharmony_ci{
12722736c2fSopenharmony_ci    auto fullInfo = FullImeInfoManager::GetInstance().Get(userId);
12822736c2fSopenharmony_ci    auto it = std::find_if(fullInfo.begin(), fullInfo.end(),
12922736c2fSopenharmony_ci        [&bundleName](const FullImeInfo &info) { return info.prop.name == bundleName; });
13022736c2fSopenharmony_ci    if (it == fullInfo.end()) {
13122736c2fSopenharmony_ci        return nullptr;
13222736c2fSopenharmony_ci    }
13322736c2fSopenharmony_ci    auto info = std::make_shared<ImeInfo>();
13422736c2fSopenharmony_ci    auto subProps = it->subProps;
13522736c2fSopenharmony_ci    info->isSpecificSubName = !subName.empty();
13622736c2fSopenharmony_ci    if (subName.empty() && !subProps.empty()) {
13722736c2fSopenharmony_ci        info->subProp = subProps[0];
13822736c2fSopenharmony_ci    } else {
13922736c2fSopenharmony_ci        auto iter = std::find_if(subProps.begin(), subProps.end(),
14022736c2fSopenharmony_ci            [&subName](const SubProperty &subProp) { return subProp.id == subName; });
14122736c2fSopenharmony_ci        if (iter == subProps.end()) {
14222736c2fSopenharmony_ci            IMSA_HILOGE("find subName: %{public}s failed!", subName.c_str());
14322736c2fSopenharmony_ci            return nullptr;
14422736c2fSopenharmony_ci        }
14522736c2fSopenharmony_ci        info->subProp = *iter;
14622736c2fSopenharmony_ci    }
14722736c2fSopenharmony_ci    info->isNewIme = it->isNewIme;
14822736c2fSopenharmony_ci    info->subProps = it->subProps;
14922736c2fSopenharmony_ci    info->prop = it->prop;
15022736c2fSopenharmony_ci    if (!info->isNewIme) {
15122736c2fSopenharmony_ci        // old ime, make the id of prop same with the id of subProp.
15222736c2fSopenharmony_ci        info->prop.id = info->subProp.id;
15322736c2fSopenharmony_ci    }
15422736c2fSopenharmony_ci    return info;
15522736c2fSopenharmony_ci}
15622736c2fSopenharmony_ci
15722736c2fSopenharmony_cistd::shared_ptr<ImeInfo> ImeInfoInquirer::GetImeInfoFromBundleMgr(
15822736c2fSopenharmony_ci    const int32_t userId, const std::string &bundleName, const std::string &subName)
15922736c2fSopenharmony_ci{
16022736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d, bundleName: %{public}s, subName: %{public}s.", userId, bundleName.c_str(),
16122736c2fSopenharmony_ci        subName.c_str());
16222736c2fSopenharmony_ci    std::vector<AppExecFwk::ExtensionAbilityInfo> extInfos;
16322736c2fSopenharmony_ci    auto ret = ImeInfoInquirer::GetInstance().GetExtInfosByBundleName(userId, bundleName, extInfos);
16422736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR || extInfos.empty()) {
16522736c2fSopenharmony_ci        IMSA_HILOGE("userId: %{public}d getExtInfosByBundleName %{public}s failed!", userId, bundleName.c_str());
16622736c2fSopenharmony_ci        return nullptr;
16722736c2fSopenharmony_ci    }
16822736c2fSopenharmony_ci    auto info = std::make_shared<ImeInfo>();
16922736c2fSopenharmony_ci    info->prop.name = extInfos[0].bundleName;
17022736c2fSopenharmony_ci    info->prop.id = extInfos[0].name;
17122736c2fSopenharmony_ci    info->prop.label = GetTargetString(extInfos[0], ImeTargetString::LABEL, userId);
17222736c2fSopenharmony_ci    info->prop.labelId = extInfos[0].applicationInfo.labelId;
17322736c2fSopenharmony_ci    info->prop.iconId = extInfos[0].applicationInfo.iconId;
17422736c2fSopenharmony_ci
17522736c2fSopenharmony_ci    std::vector<SubProperty> subProps;
17622736c2fSopenharmony_ci    info->isNewIme = IsNewExtInfos(extInfos);
17722736c2fSopenharmony_ci    ret = info->isNewIme ? ListInputMethodSubtype(userId, extInfos[0], subProps)
17822736c2fSopenharmony_ci                         : ListInputMethodSubtype(userId, extInfos, subProps);
17922736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR || subProps.empty()) {
18022736c2fSopenharmony_ci        IMSA_HILOGE("userId: %{public}d listInputMethodSubtype failed!", userId);
18122736c2fSopenharmony_ci        return nullptr;
18222736c2fSopenharmony_ci    }
18322736c2fSopenharmony_ci    info->subProps = subProps;
18422736c2fSopenharmony_ci    if (subName.empty()) {
18522736c2fSopenharmony_ci        info->isSpecificSubName = false;
18622736c2fSopenharmony_ci        info->subProp = subProps[0];
18722736c2fSopenharmony_ci    } else {
18822736c2fSopenharmony_ci        auto it = std::find_if(subProps.begin(), subProps.end(),
18922736c2fSopenharmony_ci            [&subName](const SubProperty &subProp) { return subProp.id == subName; });
19022736c2fSopenharmony_ci        if (it == subProps.end()) {
19122736c2fSopenharmony_ci            IMSA_HILOGE("find subName: %{public}s failed!", subName.c_str());
19222736c2fSopenharmony_ci            return nullptr;
19322736c2fSopenharmony_ci        }
19422736c2fSopenharmony_ci        info->subProp = *it;
19522736c2fSopenharmony_ci    }
19622736c2fSopenharmony_ci    // old ime, make the id of prop same with the id of subProp.
19722736c2fSopenharmony_ci    if (!info->isNewIme) {
19822736c2fSopenharmony_ci        info->prop.id = info->subProp.id;
19922736c2fSopenharmony_ci    }
20022736c2fSopenharmony_ci    return info;
20122736c2fSopenharmony_ci}
20222736c2fSopenharmony_ci
20322736c2fSopenharmony_cistd::string ImeInfoInquirer::GetDumpInfo(int32_t userId)
20422736c2fSopenharmony_ci{
20522736c2fSopenharmony_ci    auto properties = ListInputMethodInfo(userId);
20622736c2fSopenharmony_ci    if (properties.empty()) {
20722736c2fSopenharmony_ci        return "";
20822736c2fSopenharmony_ci    }
20922736c2fSopenharmony_ci    auto currentImeCfg = ImeCfgManager::GetInstance().GetCurrentImeCfg(userId);
21022736c2fSopenharmony_ci    bool isBegin = true;
21122736c2fSopenharmony_ci    std::string params = "{\"imeList\":[";
21222736c2fSopenharmony_ci    for (const auto &property : properties) {
21322736c2fSopenharmony_ci        params += isBegin ? "" : "},";
21422736c2fSopenharmony_ci        isBegin = false;
21522736c2fSopenharmony_ci
21622736c2fSopenharmony_ci        std::string imeId = property.mPackageName + "/" + property.mAbilityName;
21722736c2fSopenharmony_ci        params += "{\"ime\": \"" + imeId + "\",";
21822736c2fSopenharmony_ci        params += "\"labelId\": \"" + std::to_string(property.labelId) + "\",";
21922736c2fSopenharmony_ci        params += "\"descriptionId\": \"" + std::to_string(property.descriptionId) + "\",";
22022736c2fSopenharmony_ci        std::string isCurrentIme = currentImeCfg->imeId == imeId ? "true" : "false";
22122736c2fSopenharmony_ci        params += "\"isCurrentIme\": \"" + isCurrentIme + "\",";
22222736c2fSopenharmony_ci        params += "\"label\": \"" + property.label + "\",";
22322736c2fSopenharmony_ci        params += "\"description\": \"" + property.description + "\"";
22422736c2fSopenharmony_ci    }
22522736c2fSopenharmony_ci    params += "}]}";
22622736c2fSopenharmony_ci    return params;
22722736c2fSopenharmony_ci}
22822736c2fSopenharmony_ci
22922736c2fSopenharmony_cistd::vector<InputMethodInfo> ImeInfoInquirer::ListInputMethodInfo(const int32_t userId)
23022736c2fSopenharmony_ci{
23122736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d.", userId);
23222736c2fSopenharmony_ci    std::vector<ExtensionAbilityInfo> extensionInfos;
23322736c2fSopenharmony_ci    if (!QueryImeExtInfos(userId, extensionInfos)) {
23422736c2fSopenharmony_ci        IMSA_HILOGE("userId: %{public}d queryImeExtInfos failed!", userId);
23522736c2fSopenharmony_ci        return {};
23622736c2fSopenharmony_ci    }
23722736c2fSopenharmony_ci    std::vector<InputMethodInfo> properties;
23822736c2fSopenharmony_ci    for (const auto &extension : extensionInfos) {
23922736c2fSopenharmony_ci        auto applicationInfo = extension.applicationInfo;
24022736c2fSopenharmony_ci        auto label = GetTargetString(extension, ImeTargetString::LABEL, userId);
24122736c2fSopenharmony_ci        auto description = GetTargetString(extension, ImeTargetString::DESCRIPTION, userId);
24222736c2fSopenharmony_ci        InputMethodInfo property;
24322736c2fSopenharmony_ci        property.mPackageName = extension.bundleName;
24422736c2fSopenharmony_ci        property.mAbilityName = extension.name;
24522736c2fSopenharmony_ci        property.labelId = applicationInfo.labelId;
24622736c2fSopenharmony_ci        property.descriptionId = applicationInfo.descriptionId;
24722736c2fSopenharmony_ci        property.label = label;
24822736c2fSopenharmony_ci        property.description = description;
24922736c2fSopenharmony_ci        properties.emplace_back(property);
25022736c2fSopenharmony_ci    }
25122736c2fSopenharmony_ci    return properties;
25222736c2fSopenharmony_ci}
25322736c2fSopenharmony_ci
25422736c2fSopenharmony_ciint32_t ImeInfoInquirer::ListInputMethod(int32_t userId, InputMethodStatus status, std::vector<Property> &props,
25522736c2fSopenharmony_ci    bool enableOn)
25622736c2fSopenharmony_ci{
25722736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d, status: %{public}d.", userId, status);
25822736c2fSopenharmony_ci    if (status == InputMethodStatus::ALL) {
25922736c2fSopenharmony_ci        return ListInputMethod(userId, props);
26022736c2fSopenharmony_ci    }
26122736c2fSopenharmony_ci    if (status == InputMethodStatus::ENABLE) {
26222736c2fSopenharmony_ci        return ListEnabledInputMethod(userId, props, enableOn);
26322736c2fSopenharmony_ci    }
26422736c2fSopenharmony_ci    if (status == InputMethodStatus::DISABLE) {
26522736c2fSopenharmony_ci        return ListDisabledInputMethod(userId, props, enableOn);
26622736c2fSopenharmony_ci    }
26722736c2fSopenharmony_ci    return ErrorCode::ERROR_BAD_PARAMETERS;
26822736c2fSopenharmony_ci}
26922736c2fSopenharmony_ci
27022736c2fSopenharmony_ciint32_t ImeInfoInquirer::ListInputMethod(const int32_t userId, std::vector<Property> &props)
27122736c2fSopenharmony_ci{
27222736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d.", userId);
27322736c2fSopenharmony_ci    auto infos = FullImeInfoManager::GetInstance().Get(userId);
27422736c2fSopenharmony_ci    for (const auto &info : infos) {
27522736c2fSopenharmony_ci        props.push_back(info.prop);
27622736c2fSopenharmony_ci    }
27722736c2fSopenharmony_ci    if (!props.empty()) {
27822736c2fSopenharmony_ci        return ErrorCode::NO_ERROR;
27922736c2fSopenharmony_ci    }
28022736c2fSopenharmony_ci
28122736c2fSopenharmony_ci    IMSA_HILOGD("%{public}d get all prop form bms.", userId);
28222736c2fSopenharmony_ci    std::vector<ExtensionAbilityInfo> extensionInfos;
28322736c2fSopenharmony_ci    if (!QueryImeExtInfos(userId, extensionInfos)) {
28422736c2fSopenharmony_ci        IMSA_HILOGE("failed to QueryImeExtInfos!");
28522736c2fSopenharmony_ci        return ErrorCode::ERROR_BAD_PARAMETERS;
28622736c2fSopenharmony_ci    }
28722736c2fSopenharmony_ci    for (const auto &extension : extensionInfos) {
28822736c2fSopenharmony_ci        auto it = std::find_if(props.begin(), props.end(),
28922736c2fSopenharmony_ci            [&extension](const Property &prop) { return prop.name == extension.bundleName; });
29022736c2fSopenharmony_ci        if (it != props.end()) {
29122736c2fSopenharmony_ci            continue;
29222736c2fSopenharmony_ci        }
29322736c2fSopenharmony_ci        if (IsTempInputMethod(extension)) {
29422736c2fSopenharmony_ci            continue;
29522736c2fSopenharmony_ci        }
29622736c2fSopenharmony_ci        props.push_back({ .name = extension.bundleName,
29722736c2fSopenharmony_ci            .id = extension.name,
29822736c2fSopenharmony_ci            .label = GetTargetString(extension, ImeTargetString::LABEL, userId),
29922736c2fSopenharmony_ci            .labelId = extension.applicationInfo.labelId,
30022736c2fSopenharmony_ci            .iconId = extension.applicationInfo.iconId });
30122736c2fSopenharmony_ci    }
30222736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
30322736c2fSopenharmony_ci}
30422736c2fSopenharmony_ci
30522736c2fSopenharmony_ciint32_t ImeInfoInquirer::ListEnabledInputMethod(const int32_t userId, std::vector<Property> &props, bool enableOn)
30622736c2fSopenharmony_ci{
30722736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d.", userId);
30822736c2fSopenharmony_ci    int32_t ret = ListInputMethod(userId, props);
30922736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR) {
31022736c2fSopenharmony_ci        IMSA_HILOGE("userId: %{public}d listInputMethod failed!", userId);
31122736c2fSopenharmony_ci        return ret;
31222736c2fSopenharmony_ci    }
31322736c2fSopenharmony_ci    if (enableOn) {
31422736c2fSopenharmony_ci        IMSA_HILOGD("enable on.");
31522736c2fSopenharmony_ci        std::vector<std::string> enableVec;
31622736c2fSopenharmony_ci        ret = EnableImeDataParser::GetInstance()->GetEnableIme(userId, enableVec);
31722736c2fSopenharmony_ci        if (ret != ErrorCode::NO_ERROR) {
31822736c2fSopenharmony_ci            IMSA_HILOGE("get enable data failed!");
31922736c2fSopenharmony_ci            return ret;
32022736c2fSopenharmony_ci        }
32122736c2fSopenharmony_ci        auto info = GetDefaultIme();
32222736c2fSopenharmony_ci        enableVec.insert(enableVec.begin(), info.bundleName);
32322736c2fSopenharmony_ci
32422736c2fSopenharmony_ci        auto newEnd = std::remove_if(props.begin(), props.end(), [&enableVec](const auto &prop) {
32522736c2fSopenharmony_ci            return std::find(enableVec.begin(), enableVec.end(), prop.name) == enableVec.end();
32622736c2fSopenharmony_ci        });
32722736c2fSopenharmony_ci        props.erase(newEnd, props.end());
32822736c2fSopenharmony_ci    }
32922736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
33022736c2fSopenharmony_ci}
33122736c2fSopenharmony_ci
33222736c2fSopenharmony_ciint32_t ImeInfoInquirer::ListDisabledInputMethod(const int32_t userId, std::vector<Property> &props, bool enableOn)
33322736c2fSopenharmony_ci{
33422736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d.", userId);
33522736c2fSopenharmony_ci    if (!enableOn) {
33622736c2fSopenharmony_ci        IMSA_HILOGD("enable mode off, get disabled ime.");
33722736c2fSopenharmony_ci        return ErrorCode::NO_ERROR;
33822736c2fSopenharmony_ci    }
33922736c2fSopenharmony_ci
34022736c2fSopenharmony_ci    auto ret = ListInputMethod(userId, props);
34122736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR) {
34222736c2fSopenharmony_ci        IMSA_HILOGE("userId: %{public}d listInputMethod failed!", userId);
34322736c2fSopenharmony_ci        return ret;
34422736c2fSopenharmony_ci    }
34522736c2fSopenharmony_ci
34622736c2fSopenharmony_ci    std::vector<std::string> enableVec;
34722736c2fSopenharmony_ci    ret = EnableImeDataParser::GetInstance()->GetEnableIme(userId, enableVec);
34822736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR) {
34922736c2fSopenharmony_ci        IMSA_HILOGE("get enable data failed!");
35022736c2fSopenharmony_ci        return ret;
35122736c2fSopenharmony_ci    }
35222736c2fSopenharmony_ci    auto info = GetDefaultIme();
35322736c2fSopenharmony_ci    enableVec.insert(enableVec.begin(), info.bundleName);
35422736c2fSopenharmony_ci
35522736c2fSopenharmony_ci    auto newEnd = std::remove_if(props.begin(), props.end(), [&enableVec](const auto &prop) {
35622736c2fSopenharmony_ci        return std::find(enableVec.begin(), enableVec.end(), prop.name) != enableVec.end();
35722736c2fSopenharmony_ci    });
35822736c2fSopenharmony_ci    props.erase(newEnd, props.end());
35922736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
36022736c2fSopenharmony_ci}
36122736c2fSopenharmony_ci
36222736c2fSopenharmony_ciint32_t ImeInfoInquirer::GetSwitchInfoBySwitchCount(SwitchInfo &switchInfo, int32_t userId, bool enableOn,
36322736c2fSopenharmony_ci    uint32_t cacheCount)
36422736c2fSopenharmony_ci{
36522736c2fSopenharmony_ci    std::vector<Property> props;
36622736c2fSopenharmony_ci    auto ret = ListEnabledInputMethod(userId, props, enableOn);
36722736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR) {
36822736c2fSopenharmony_ci        IMSA_HILOGE("userId: %{public}d ListEnabledInputMethod failed!", userId);
36922736c2fSopenharmony_ci        return ret;
37022736c2fSopenharmony_ci    }
37122736c2fSopenharmony_ci    auto currentImeBundle = ImeCfgManager::GetInstance().GetCurrentImeCfg(userId)->bundleName;
37222736c2fSopenharmony_ci    auto iter = std::find_if(props.begin(), props.end(),
37322736c2fSopenharmony_ci        [&currentImeBundle](const Property &property) { return property.name == currentImeBundle; });
37422736c2fSopenharmony_ci    if (iter == props.end()) {
37522736c2fSopenharmony_ci        IMSA_HILOGE("can not found current ime in enable list!");
37622736c2fSopenharmony_ci        auto info = GetDefaultImeInfo(userId);
37722736c2fSopenharmony_ci        if (info != nullptr) {
37822736c2fSopenharmony_ci            switchInfo.bundleName = info->prop.name;
37922736c2fSopenharmony_ci            return ErrorCode::NO_ERROR;
38022736c2fSopenharmony_ci        }
38122736c2fSopenharmony_ci        IMSA_HILOGE("bundle manager error!");
38222736c2fSopenharmony_ci        return ErrorCode::ERROR_PACKAGE_MANAGER;
38322736c2fSopenharmony_ci    }
38422736c2fSopenharmony_ci    uint32_t nextIndex = (cacheCount + static_cast<uint32_t>(std::distance(props.begin(), iter))) % props.size();
38522736c2fSopenharmony_ci    switchInfo.bundleName = props[nextIndex].name;
38622736c2fSopenharmony_ci    IMSA_HILOGD("next ime: %{public}s", switchInfo.bundleName.c_str());
38722736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
38822736c2fSopenharmony_ci}
38922736c2fSopenharmony_ci
39022736c2fSopenharmony_ciint32_t ImeInfoInquirer::ListInputMethodSubtype(int32_t userId, const std::string &bundleName,
39122736c2fSopenharmony_ci    std::vector<SubProperty> &subProps)
39222736c2fSopenharmony_ci{
39322736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d, bundleName: %{public}s.", userId, bundleName.c_str());
39422736c2fSopenharmony_ci    auto infos = FullImeInfoManager::GetInstance().Get(userId);
39522736c2fSopenharmony_ci    auto it = std::find_if(
39622736c2fSopenharmony_ci        infos.begin(), infos.end(), [&bundleName](const FullImeInfo &info) { return info.prop.name == bundleName; });
39722736c2fSopenharmony_ci    if (it != infos.end()) {
39822736c2fSopenharmony_ci        subProps = (*it).subProps;
39922736c2fSopenharmony_ci        return ErrorCode::NO_ERROR;
40022736c2fSopenharmony_ci    }
40122736c2fSopenharmony_ci
40222736c2fSopenharmony_ci    IMSA_HILOGD("%{public}d get %{public}s all subProp form bms.", userId, bundleName.c_str());
40322736c2fSopenharmony_ci    std::vector<ExtensionAbilityInfo> extInfos;
40422736c2fSopenharmony_ci    auto ret = GetExtInfosByBundleName(userId, bundleName, extInfos);
40522736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR) {
40622736c2fSopenharmony_ci        IMSA_HILOGE("userId: %{public}d getExtInfosByBundleName %{public}s failed!", userId, bundleName.c_str());
40722736c2fSopenharmony_ci        return ret;
40822736c2fSopenharmony_ci    }
40922736c2fSopenharmony_ci    return IsNewExtInfos(extInfos) ? ListInputMethodSubtype(userId, extInfos[0], subProps)
41022736c2fSopenharmony_ci                                   : ListInputMethodSubtype(userId, extInfos, subProps);
41122736c2fSopenharmony_ci}
41222736c2fSopenharmony_ci
41322736c2fSopenharmony_ciint32_t ImeInfoInquirer::ListCurrentInputMethodSubtype(int32_t userId, std::vector<SubProperty> &subProps)
41422736c2fSopenharmony_ci{
41522736c2fSopenharmony_ci    auto currentImeCfg = ImeCfgManager::GetInstance().GetCurrentImeCfg(userId);
41622736c2fSopenharmony_ci    IMSA_HILOGD("currentIme: %{public}s.", currentImeCfg->imeId.c_str());
41722736c2fSopenharmony_ci    return ListInputMethodSubtype(userId, currentImeCfg->bundleName, subProps);
41822736c2fSopenharmony_ci}
41922736c2fSopenharmony_ci
42022736c2fSopenharmony_cibool ImeInfoInquirer::IsNewExtInfos(const std::vector<ExtensionAbilityInfo> &extInfos)
42122736c2fSopenharmony_ci{
42222736c2fSopenharmony_ci    if (extInfos.empty()) {
42322736c2fSopenharmony_ci        IMSA_HILOGE("extInfos is empty!");
42422736c2fSopenharmony_ci        return false;
42522736c2fSopenharmony_ci    }
42622736c2fSopenharmony_ci    auto iter = std::find_if(extInfos[0].metadata.begin(), extInfos[0].metadata.end(),
42722736c2fSopenharmony_ci        [](const Metadata &metadata) { return metadata.name == SUBTYPE_PROFILE_METADATA_NAME; });
42822736c2fSopenharmony_ci    return iter != extInfos[0].metadata.end();
42922736c2fSopenharmony_ci}
43022736c2fSopenharmony_ci
43122736c2fSopenharmony_ciint32_t ImeInfoInquirer::GetSubProperty(int32_t userId, const std::string &subName,
43222736c2fSopenharmony_ci    const std::vector<OHOS::AppExecFwk::ExtensionAbilityInfo> &extInfos, SubProperty &subProp)
43322736c2fSopenharmony_ci{
43422736c2fSopenharmony_ci    IMSA_HILOGD("oldIme, userId: %{public}d.", userId);
43522736c2fSopenharmony_ci    if (extInfos.empty()) {
43622736c2fSopenharmony_ci        IMSA_HILOGE("extInfos is empty!");
43722736c2fSopenharmony_ci        return ErrorCode::ERROR_PACKAGE_MANAGER;
43822736c2fSopenharmony_ci    }
43922736c2fSopenharmony_ci    auto extInfo = std::find_if(extInfos.begin(), extInfos.end(),
44022736c2fSopenharmony_ci        [&subName](const ExtensionAbilityInfo &info) { return info.name == subName; });
44122736c2fSopenharmony_ci    if (extInfo == extInfos.end()) {
44222736c2fSopenharmony_ci        IMSA_HILOGE("subtype %{public}s not found!", subName.c_str());
44322736c2fSopenharmony_ci        extInfo = extInfos.begin();
44422736c2fSopenharmony_ci    }
44522736c2fSopenharmony_ci    subProp.labelId = extInfo->labelId;
44622736c2fSopenharmony_ci    subProp.label = GetStringById(extInfo->bundleName, extInfo->moduleName, extInfo->labelId, userId);
44722736c2fSopenharmony_ci    subProp.id = extInfo->name;
44822736c2fSopenharmony_ci    subProp.name = extInfo->bundleName;
44922736c2fSopenharmony_ci    subProp.iconId = extInfo->iconId;
45022736c2fSopenharmony_ci    std::vector<Metadata> extends = extInfo->metadata;
45122736c2fSopenharmony_ci    auto property = GetExtends(extends);
45222736c2fSopenharmony_ci    subProp.language = property.language;
45322736c2fSopenharmony_ci    subProp.mode = property.mode;
45422736c2fSopenharmony_ci    subProp.locale = property.locale;
45522736c2fSopenharmony_ci    subProp.icon = property.icon;
45622736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
45722736c2fSopenharmony_ci}
45822736c2fSopenharmony_ci
45922736c2fSopenharmony_ciint32_t ImeInfoInquirer::ListInputMethodSubtype(const int32_t userId,
46022736c2fSopenharmony_ci    const std::vector<ExtensionAbilityInfo> &extInfos, std::vector<SubProperty> &subProps)
46122736c2fSopenharmony_ci{
46222736c2fSopenharmony_ci    IMSA_HILOGD("oldIme, userId: %{public}d.", userId);
46322736c2fSopenharmony_ci    for (const auto &extInfo : extInfos) {
46422736c2fSopenharmony_ci        SubProperty subProperty;
46522736c2fSopenharmony_ci        subProperty.labelId = extInfo.labelId;
46622736c2fSopenharmony_ci        subProperty.label = GetStringById(extInfo.bundleName, extInfo.moduleName, extInfo.labelId, userId);
46722736c2fSopenharmony_ci        subProperty.id = extInfo.name;
46822736c2fSopenharmony_ci        subProperty.name = extInfo.bundleName;
46922736c2fSopenharmony_ci        subProperty.iconId = extInfo.iconId;
47022736c2fSopenharmony_ci        std::vector<Metadata> extends = extInfo.metadata;
47122736c2fSopenharmony_ci        auto property = GetExtends(extends);
47222736c2fSopenharmony_ci        subProperty.language = property.language;
47322736c2fSopenharmony_ci        subProperty.mode = property.mode;
47422736c2fSopenharmony_ci        subProperty.locale = property.locale;
47522736c2fSopenharmony_ci        subProperty.icon = property.icon;
47622736c2fSopenharmony_ci        subProps.emplace_back(subProperty);
47722736c2fSopenharmony_ci    }
47822736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
47922736c2fSopenharmony_ci}
48022736c2fSopenharmony_ci
48122736c2fSopenharmony_ciint32_t ImeInfoInquirer::GetSubProperty(int32_t userId, const std::string &subName,
48222736c2fSopenharmony_ci    const OHOS::AppExecFwk::ExtensionAbilityInfo &extInfo, SubProperty &subProp)
48322736c2fSopenharmony_ci{
48422736c2fSopenharmony_ci    IMSA_HILOGD("newIme, userId: %{public}d.", userId);
48522736c2fSopenharmony_ci    std::vector<Subtype> subtypes;
48622736c2fSopenharmony_ci    auto ret = ParseSubtype(extInfo, subtypes);
48722736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR) {
48822736c2fSopenharmony_ci        IMSA_HILOGE("failed to parse subtype!");
48922736c2fSopenharmony_ci        return ret;
49022736c2fSopenharmony_ci    }
49122736c2fSopenharmony_ci    if (subtypes.empty()) {
49222736c2fSopenharmony_ci        IMSA_HILOGE("subtypes is empty!");
49322736c2fSopenharmony_ci        return ErrorCode::ERROR_PACKAGE_MANAGER;
49422736c2fSopenharmony_ci    }
49522736c2fSopenharmony_ci    auto subtype = std::find_if(
49622736c2fSopenharmony_ci        subtypes.begin(), subtypes.end(), [&subName](const Subtype &subtype) { return subtype.id == subName; });
49722736c2fSopenharmony_ci    if (subtype == subtypes.end()) {
49822736c2fSopenharmony_ci        IMSA_HILOGE("subtype %{public}s not found!", subName.c_str());
49922736c2fSopenharmony_ci        subtype = subtypes.begin();
50022736c2fSopenharmony_ci    }
50122736c2fSopenharmony_ci    subProp.label = subtype->label;
50222736c2fSopenharmony_ci    subProp.name = extInfo.bundleName;
50322736c2fSopenharmony_ci    subProp.id = subtype->id;
50422736c2fSopenharmony_ci    subProp.mode = subtype->mode;
50522736c2fSopenharmony_ci    subProp.locale = subtype->locale;
50622736c2fSopenharmony_ci    subProp.icon = subtype->icon;
50722736c2fSopenharmony_ci    auto pos = subProp.label.find(':');
50822736c2fSopenharmony_ci    if (pos != std::string::npos && pos + 1 < subProp.label.size()) {
50922736c2fSopenharmony_ci        int32_t labelId = atoi(subProp.label.substr(pos + 1).c_str());
51022736c2fSopenharmony_ci        if (labelId > 0) {
51122736c2fSopenharmony_ci            subProp.labelId = static_cast<uint32_t>(labelId);
51222736c2fSopenharmony_ci            subProp.label = GetStringById(extInfo.bundleName, extInfo.moduleName, subProp.labelId, userId);
51322736c2fSopenharmony_ci        }
51422736c2fSopenharmony_ci    }
51522736c2fSopenharmony_ci    pos = subProp.icon.find(':');
51622736c2fSopenharmony_ci    if (pos != std::string::npos && pos + 1 < subProp.icon.size()) {
51722736c2fSopenharmony_ci        int32_t iconId = atoi(subProp.icon.substr(pos + 1).c_str());
51822736c2fSopenharmony_ci        if (iconId > 0) {
51922736c2fSopenharmony_ci            subProp.iconId = static_cast<uint32_t>(iconId);
52022736c2fSopenharmony_ci        }
52122736c2fSopenharmony_ci    }
52222736c2fSopenharmony_ci    CovertToLanguage(subProp.locale, subProp.language);
52322736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
52422736c2fSopenharmony_ci}
52522736c2fSopenharmony_ci
52622736c2fSopenharmony_ciint32_t ImeInfoInquirer::ListInputMethodSubtype(const int32_t userId, const ExtensionAbilityInfo &extInfo,
52722736c2fSopenharmony_ci    std::vector<SubProperty> &subProps)
52822736c2fSopenharmony_ci{
52922736c2fSopenharmony_ci    IMSA_HILOGD("newIme, userId: %{public}d.", userId);
53022736c2fSopenharmony_ci    std::vector<Subtype> subtypes;
53122736c2fSopenharmony_ci    auto ret = ParseSubtype(extInfo, subtypes);
53222736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR) {
53322736c2fSopenharmony_ci        IMSA_HILOGE("failed to parse subtype!");
53422736c2fSopenharmony_ci        return ret;
53522736c2fSopenharmony_ci    }
53622736c2fSopenharmony_ci
53722736c2fSopenharmony_ci    std::string resPath = extInfo.hapPath.empty() ? extInfo.resourcePath : extInfo.hapPath;
53822736c2fSopenharmony_ci    auto resMgr = GetResMgr(resPath);
53922736c2fSopenharmony_ci    IMSA_HILOGD("subtypes size: %{public}zu.", subtypes.size());
54022736c2fSopenharmony_ci    for (const auto &subtype : subtypes) {
54122736c2fSopenharmony_ci        // subtype which provides a particular input type should not appear in the subtype list
54222736c2fSopenharmony_ci        if (InputTypeManager::GetInstance().IsInputType({ extInfo.bundleName, subtype.id })) {
54322736c2fSopenharmony_ci            continue;
54422736c2fSopenharmony_ci        }
54522736c2fSopenharmony_ci        SubProperty subProp{ .label = subtype.label,
54622736c2fSopenharmony_ci            .name = extInfo.bundleName,
54722736c2fSopenharmony_ci            .id = subtype.id,
54822736c2fSopenharmony_ci            .mode = subtype.mode,
54922736c2fSopenharmony_ci            .locale = subtype.locale,
55022736c2fSopenharmony_ci            .icon = subtype.icon };
55122736c2fSopenharmony_ci        auto pos = subProp.label.find(':');
55222736c2fSopenharmony_ci        if (pos != std::string::npos && pos + 1 < subProp.label.size()) {
55322736c2fSopenharmony_ci            int32_t labelId = atoi(subProp.label.substr(pos + 1).c_str());
55422736c2fSopenharmony_ci            if (labelId > 0) {
55522736c2fSopenharmony_ci                subProp.labelId = static_cast<uint32_t>(labelId);
55622736c2fSopenharmony_ci            }
55722736c2fSopenharmony_ci        }
55822736c2fSopenharmony_ci        if (resMgr != nullptr) {
55922736c2fSopenharmony_ci            auto errValue = resMgr->GetStringById(subProp.labelId, subProp.label);
56022736c2fSopenharmony_ci            if (errValue != RState::SUCCESS) {
56122736c2fSopenharmony_ci                IMSA_HILOGE("GetStringById failed, bundleName:%{public}s, id:%{public}d.", extInfo.bundleName.c_str(),
56222736c2fSopenharmony_ci                    subProp.labelId);
56322736c2fSopenharmony_ci            }
56422736c2fSopenharmony_ci        }
56522736c2fSopenharmony_ci        pos = subProp.icon.find(':');
56622736c2fSopenharmony_ci        if (pos != std::string::npos && pos + 1 < subProp.icon.size()) {
56722736c2fSopenharmony_ci            int32_t iconId = atoi(subProp.icon.substr(pos + 1).c_str());
56822736c2fSopenharmony_ci            if (iconId > 0) {
56922736c2fSopenharmony_ci                subProp.iconId = static_cast<uint32_t>(iconId);
57022736c2fSopenharmony_ci            }
57122736c2fSopenharmony_ci        }
57222736c2fSopenharmony_ci        CovertToLanguage(subProp.locale, subProp.language);
57322736c2fSopenharmony_ci        subProps.emplace_back(subProp);
57422736c2fSopenharmony_ci    }
57522736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
57622736c2fSopenharmony_ci}
57722736c2fSopenharmony_ci
57822736c2fSopenharmony_ciint32_t ImeInfoInquirer::ParseSubtype(const OHOS::AppExecFwk::ExtensionAbilityInfo &extInfo,
57922736c2fSopenharmony_ci    std::vector<Subtype> &subtypes)
58022736c2fSopenharmony_ci{
58122736c2fSopenharmony_ci    if (extInfo.metadata.empty()) {
58222736c2fSopenharmony_ci        IMSA_HILOGE("metadata is empty!");
58322736c2fSopenharmony_ci        return ErrorCode::ERROR_BAD_PARAMETERS;
58422736c2fSopenharmony_ci    }
58522736c2fSopenharmony_ci    auto iter = std::find_if(extInfo.metadata.begin(), extInfo.metadata.end(),
58622736c2fSopenharmony_ci        [](const Metadata &metadata) { return metadata.name == SUBTYPE_PROFILE_METADATA_NAME; });
58722736c2fSopenharmony_ci    if (iter == extInfo.metadata.end()) {
58822736c2fSopenharmony_ci        IMSA_HILOGE("find metadata name: SUBTYPE_PROFILE_METADATA_NAME failed!");
58922736c2fSopenharmony_ci        return ErrorCode::ERROR_BAD_PARAMETERS;
59022736c2fSopenharmony_ci    }
59122736c2fSopenharmony_ci    OHOS::AppExecFwk::BundleMgrClientImpl clientImpl;
59222736c2fSopenharmony_ci    std::vector<std::string> profiles;
59322736c2fSopenharmony_ci    if (!clientImpl.GetResConfigFile(extInfo, iter->name, profiles)) {
59422736c2fSopenharmony_ci        IMSA_HILOGE("failed to GetProfileFromExtension!");
59522736c2fSopenharmony_ci        return ErrorCode::ERROR_PACKAGE_MANAGER;
59622736c2fSopenharmony_ci    }
59722736c2fSopenharmony_ci    SubtypeCfg subtypeCfg;
59822736c2fSopenharmony_ci    if (!ParseSubtypeProfile(profiles, subtypeCfg)) {
59922736c2fSopenharmony_ci        IMSA_HILOGE("failed to ParseSubTypeCfg!");
60022736c2fSopenharmony_ci        return ErrorCode::ERROR_BAD_PARAMETERS;
60122736c2fSopenharmony_ci    }
60222736c2fSopenharmony_ci    subtypes = subtypeCfg.subtypes;
60322736c2fSopenharmony_ci    IMSA_HILOGD("success.");
60422736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
60522736c2fSopenharmony_ci}
60622736c2fSopenharmony_ci
60722736c2fSopenharmony_civoid ImeInfoInquirer::CovertToLanguage(const std::string &locale, std::string &language)
60822736c2fSopenharmony_ci{
60922736c2fSopenharmony_ci    language = locale;
61022736c2fSopenharmony_ci    auto pos = locale.find('-');
61122736c2fSopenharmony_ci    if (pos != std::string::npos) {
61222736c2fSopenharmony_ci        language = locale.substr(0, pos);
61322736c2fSopenharmony_ci    }
61422736c2fSopenharmony_ci    // compatible with the locale configuration of original ime
61522736c2fSopenharmony_ci    pos = locale.find('_');
61622736c2fSopenharmony_ci    if (pos != std::string::npos) {
61722736c2fSopenharmony_ci        language = locale.substr(0, pos);
61822736c2fSopenharmony_ci    }
61922736c2fSopenharmony_ci    if (language == "en") {
62022736c2fSopenharmony_ci        language = "english";
62122736c2fSopenharmony_ci    }
62222736c2fSopenharmony_ci    if (language == "zh") {
62322736c2fSopenharmony_ci        language = "chinese";
62422736c2fSopenharmony_ci    }
62522736c2fSopenharmony_ci}
62622736c2fSopenharmony_ci
62722736c2fSopenharmony_cistd::string ImeInfoInquirer::GetStringById(const std::string &bundleName, const std::string &moduleName,
62822736c2fSopenharmony_ci    uint32_t labelId, int32_t userId)
62922736c2fSopenharmony_ci{
63022736c2fSopenharmony_ci    auto bundleMgr = GetBundleMgr();
63122736c2fSopenharmony_ci    return bundleMgr == nullptr ? "" : bundleMgr->GetStringById(bundleName, moduleName, labelId, userId);
63222736c2fSopenharmony_ci}
63322736c2fSopenharmony_ci
63422736c2fSopenharmony_ciSubProperty ImeInfoInquirer::GetExtends(const std::vector<Metadata> &metaData)
63522736c2fSopenharmony_ci{
63622736c2fSopenharmony_ci    SubProperty property;
63722736c2fSopenharmony_ci    for (const auto &data : metaData) {
63822736c2fSopenharmony_ci        if (data.name == "language") {
63922736c2fSopenharmony_ci            property.language = data.value;
64022736c2fSopenharmony_ci            continue;
64122736c2fSopenharmony_ci        }
64222736c2fSopenharmony_ci        if (data.name == "mode") {
64322736c2fSopenharmony_ci            property.mode = data.value;
64422736c2fSopenharmony_ci            continue;
64522736c2fSopenharmony_ci        }
64622736c2fSopenharmony_ci        if (data.name == "locale") {
64722736c2fSopenharmony_ci            property.locale = data.value;
64822736c2fSopenharmony_ci            continue;
64922736c2fSopenharmony_ci        }
65022736c2fSopenharmony_ci        if (data.name == "icon") {
65122736c2fSopenharmony_ci            property.icon = data.value;
65222736c2fSopenharmony_ci        }
65322736c2fSopenharmony_ci    }
65422736c2fSopenharmony_ci    return property;
65522736c2fSopenharmony_ci}
65622736c2fSopenharmony_ci
65722736c2fSopenharmony_cistd::shared_ptr<Property> ImeInfoInquirer::GetImeProperty(
65822736c2fSopenharmony_ci    int32_t userId, const std::string &bundleName, const std::string &extName)
65922736c2fSopenharmony_ci{
66022736c2fSopenharmony_ci    IMSA_HILOGD("start, bundleName: %{public}s", bundleName.c_str());
66122736c2fSopenharmony_ci    std::vector<AppExecFwk::ExtensionAbilityInfo> extInfos;
66222736c2fSopenharmony_ci    auto ret = ImeInfoInquirer::GetInstance().GetExtInfosByBundleName(userId, bundleName, extInfos);
66322736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR || extInfos.empty()) {
66422736c2fSopenharmony_ci        IMSA_HILOGE("userId: %{public}d getExtInfosByBundleName %{public}s failed!", userId, bundleName.c_str());
66522736c2fSopenharmony_ci        return nullptr;
66622736c2fSopenharmony_ci    }
66722736c2fSopenharmony_ci    Property prop = { .name = extInfos[0].bundleName,
66822736c2fSopenharmony_ci        .id = extName.empty() ? extInfos[0].name : extName,
66922736c2fSopenharmony_ci        .label = GetTargetString(extInfos[0], ImeTargetString::LABEL, userId),
67022736c2fSopenharmony_ci        .labelId = extInfos[0].applicationInfo.labelId,
67122736c2fSopenharmony_ci        .iconId = extInfos[0].applicationInfo.iconId };
67222736c2fSopenharmony_ci    return std::make_shared<Property>(prop);
67322736c2fSopenharmony_ci}
67422736c2fSopenharmony_ci
67522736c2fSopenharmony_cistd::shared_ptr<Property> ImeInfoInquirer::GetCurrentInputMethod(int32_t userId)
67622736c2fSopenharmony_ci{
67722736c2fSopenharmony_ci    auto currentImeCfg = ImeCfgManager::GetInstance().GetCurrentImeCfg(userId);
67822736c2fSopenharmony_ci    IMSA_HILOGD("currentIme: %{public}s.", currentImeCfg->imeId.c_str());
67922736c2fSopenharmony_ci    auto infos = FullImeInfoManager::GetInstance().Get(userId);
68022736c2fSopenharmony_ci    auto it = std::find_if(infos.begin(), infos.end(),
68122736c2fSopenharmony_ci        [&currentImeCfg](const FullImeInfo &info) { return info.prop.name == currentImeCfg->bundleName; });
68222736c2fSopenharmony_ci    if (it != infos.end()) {
68322736c2fSopenharmony_ci        auto prop = std::make_shared<Property>((*it).prop);
68422736c2fSopenharmony_ci        prop->id = currentImeCfg->extName;
68522736c2fSopenharmony_ci        return prop;
68622736c2fSopenharmony_ci    }
68722736c2fSopenharmony_ci
68822736c2fSopenharmony_ci    IMSA_HILOGD("%{public}d get %{public}s prop form bms.", userId, currentImeCfg->bundleName.c_str());
68922736c2fSopenharmony_ci    return GetImeProperty(userId, currentImeCfg->bundleName, currentImeCfg->extName);
69022736c2fSopenharmony_ci}
69122736c2fSopenharmony_ci
69222736c2fSopenharmony_cistd::shared_ptr<SubProperty> ImeInfoInquirer::GetCurrentSubtype(int32_t userId)
69322736c2fSopenharmony_ci{
69422736c2fSopenharmony_ci    auto currentIme = ImeCfgManager::GetInstance().GetCurrentImeCfg(userId);
69522736c2fSopenharmony_ci    IMSA_HILOGD("currentIme: %{public}s.", currentIme->imeId.c_str());
69622736c2fSopenharmony_ci    auto infos = FullImeInfoManager::GetInstance().Get(userId);
69722736c2fSopenharmony_ci    auto it = std::find_if(infos.begin(), infos.end(),
69822736c2fSopenharmony_ci        [&currentIme](const FullImeInfo &info) { return info.prop.name == currentIme->bundleName; });
69922736c2fSopenharmony_ci    if (it != infos.end() && !it->subProps.empty()) {
70022736c2fSopenharmony_ci        auto iter = std::find_if(it->subProps.begin(), it->subProps.end(),
70122736c2fSopenharmony_ci            [&currentIme](const SubProperty &subProp) { return subProp.id == currentIme->subName; });
70222736c2fSopenharmony_ci        if (iter != it->subProps.end()) {
70322736c2fSopenharmony_ci            return std::make_shared<SubProperty>(*iter);
70422736c2fSopenharmony_ci        }
70522736c2fSopenharmony_ci        IMSA_HILOGW("subtype %{public}s not found.", currentIme->subName.c_str());
70622736c2fSopenharmony_ci        ImeCfgManager::GetInstance().ModifyImeCfg({ userId, currentIme->imeId, it->subProps[0].id, false });
70722736c2fSopenharmony_ci        return std::make_shared<SubProperty>(it->subProps[0]);
70822736c2fSopenharmony_ci    }
70922736c2fSopenharmony_ci
71022736c2fSopenharmony_ci    IMSA_HILOGD("%{public}d get [%{public}s, %{public}s] form bms.", userId, currentIme->bundleName.c_str(),
71122736c2fSopenharmony_ci        currentIme->subName.c_str());
71222736c2fSopenharmony_ci    std::vector<ExtensionAbilityInfo> extInfos;
71322736c2fSopenharmony_ci    auto ret = GetExtInfosByBundleName(userId, currentIme->bundleName, extInfos);
71422736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR) {
71522736c2fSopenharmony_ci        IMSA_HILOGE("failed to GetExtInfosByBundleName: %{public}s, ret: %{public}d", currentIme->bundleName.c_str(),
71622736c2fSopenharmony_ci            ret);
71722736c2fSopenharmony_ci        return nullptr;
71822736c2fSopenharmony_ci    }
71922736c2fSopenharmony_ci    SubProperty subProp;
72022736c2fSopenharmony_ci    ret = IsNewExtInfos(extInfos) ? GetSubProperty(userId, currentIme->subName, extInfos[0], subProp)
72122736c2fSopenharmony_ci                                  : GetSubProperty(userId, currentIme->subName, extInfos, subProp);
72222736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR) {
72322736c2fSopenharmony_ci        IMSA_HILOGE("get %{public}s property failed, ret: %{public}d!", currentIme->subName.c_str(), ret);
72422736c2fSopenharmony_ci        return nullptr;
72522736c2fSopenharmony_ci    }
72622736c2fSopenharmony_ci    return std::make_shared<SubProperty>(subProp);
72722736c2fSopenharmony_ci}
72822736c2fSopenharmony_ci
72922736c2fSopenharmony_cibool ImeInfoInquirer::IsImeInstalled(const int32_t userId, const std::string &bundleName, const std::string &extName)
73022736c2fSopenharmony_ci{
73122736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d, bundleName: %{public}s, extName: %{public}s.", userId, bundleName.c_str(),
73222736c2fSopenharmony_ci        extName.c_str());
73322736c2fSopenharmony_ci    std::vector<OHOS::AppExecFwk::ExtensionAbilityInfo> extInfos;
73422736c2fSopenharmony_ci    GetExtInfosByBundleName(userId, bundleName, extInfos);
73522736c2fSopenharmony_ci    auto iter = std::find_if(extInfos.begin(), extInfos.end(),
73622736c2fSopenharmony_ci        [&bundleName, &extName](const OHOS::AppExecFwk::ExtensionAbilityInfo &extInfo) {
73722736c2fSopenharmony_ci            return extInfo.bundleName == bundleName && extName == extInfo.name;
73822736c2fSopenharmony_ci        });
73922736c2fSopenharmony_ci    if (iter == extInfos.end()) {
74022736c2fSopenharmony_ci        IMSA_HILOGE("false");
74122736c2fSopenharmony_ci        return false;
74222736c2fSopenharmony_ci    }
74322736c2fSopenharmony_ci    IMSA_HILOGI("true");
74422736c2fSopenharmony_ci    return true;
74522736c2fSopenharmony_ci}
74622736c2fSopenharmony_ci
74722736c2fSopenharmony_cistd::shared_ptr<ImeNativeCfg> ImeInfoInquirer::GetImeToStart(int32_t userId)
74822736c2fSopenharmony_ci{
74922736c2fSopenharmony_ci    auto currentImeCfg = ImeCfgManager::GetInstance().GetCurrentImeCfg(userId);
75022736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d, currentIme: %{public}s.", userId, currentImeCfg->imeId.c_str());
75122736c2fSopenharmony_ci    if (currentImeCfg->imeId.empty() || !IsImeInstalled(userId, currentImeCfg->bundleName, currentImeCfg->extName)) {
75222736c2fSopenharmony_ci        auto newIme = GetDefaultIme();
75322736c2fSopenharmony_ci        auto info = GetDefaultImeInfo(userId);
75422736c2fSopenharmony_ci        if (info == nullptr) {
75522736c2fSopenharmony_ci            IMSA_HILOGW("failed to GetDefaultImeInfo");
75622736c2fSopenharmony_ci            newIme.subName = "";
75722736c2fSopenharmony_ci        } else {
75822736c2fSopenharmony_ci            newIme.subName = info->subProp.id;
75922736c2fSopenharmony_ci        }
76022736c2fSopenharmony_ci        currentImeCfg->imeId.empty()
76122736c2fSopenharmony_ci            ? ImeCfgManager::GetInstance().AddImeCfg({ userId, newIme.imeId, newIme.subName, false })
76222736c2fSopenharmony_ci            : ImeCfgManager::GetInstance().ModifyImeCfg({ userId, newIme.imeId, newIme.subName, false});
76322736c2fSopenharmony_ci        return std::make_shared<ImeNativeCfg>(newIme);
76422736c2fSopenharmony_ci    }
76522736c2fSopenharmony_ci    return currentImeCfg;
76622736c2fSopenharmony_ci}
76722736c2fSopenharmony_ci
76822736c2fSopenharmony_ciint32_t ImeInfoInquirer::GetInputMethodConfig(const int32_t userId, AppExecFwk::ElementName &inputMethodConfig)
76922736c2fSopenharmony_ci{
77022736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d.", userId);
77122736c2fSopenharmony_ci    if (systemConfig_.systemInputMethodConfigAbility.empty()) {
77222736c2fSopenharmony_ci        IMSA_HILOGW("inputMethodConfig systemInputMethodConfigAbility is nullptr");
77322736c2fSopenharmony_ci        return ErrorCode::NO_ERROR;
77422736c2fSopenharmony_ci    }
77522736c2fSopenharmony_ci    std::string bundleName = systemConfig_.systemInputMethodConfigAbility;
77622736c2fSopenharmony_ci    std::string moduleName;
77722736c2fSopenharmony_ci    std::string abilityName;
77822736c2fSopenharmony_ci    auto pos = bundleName.find('/');
77922736c2fSopenharmony_ci    if (pos != std::string::npos) {
78022736c2fSopenharmony_ci        abilityName = (pos + 1 < bundleName.size()) ? bundleName.substr(pos + 1) : "";
78122736c2fSopenharmony_ci        bundleName = bundleName.substr(0, pos);
78222736c2fSopenharmony_ci    }
78322736c2fSopenharmony_ci    pos = abilityName.find('/');
78422736c2fSopenharmony_ci    if (pos != std::string::npos) {
78522736c2fSopenharmony_ci        moduleName = abilityName.substr(0, pos);
78622736c2fSopenharmony_ci        abilityName = (pos + 1 < abilityName.size()) ? abilityName.substr(pos + 1) : "";
78722736c2fSopenharmony_ci    }
78822736c2fSopenharmony_ci    inputMethodConfig.SetBundleName(std::move(bundleName));
78922736c2fSopenharmony_ci    inputMethodConfig.SetModuleName(std::move(moduleName));
79022736c2fSopenharmony_ci    inputMethodConfig.SetAbilityName(std::move(abilityName));
79122736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
79222736c2fSopenharmony_ci}
79322736c2fSopenharmony_ci
79422736c2fSopenharmony_ciint32_t ImeInfoInquirer::GetDefaultInputMethod(const int32_t userId, std::shared_ptr<Property> &prop, bool isBrief)
79522736c2fSopenharmony_ci{
79622736c2fSopenharmony_ci    IMSA_HILOGD("userId: %{public}d.", userId);
79722736c2fSopenharmony_ci    auto defaultIme = GetDefaultImeCfgProp();
79822736c2fSopenharmony_ci    if (defaultIme == nullptr) {
79922736c2fSopenharmony_ci        IMSA_HILOGE("abnormal default ime cfg!");
80022736c2fSopenharmony_ci        return ErrorCode::ERROR_NULL_POINTER;
80122736c2fSopenharmony_ci    }
80222736c2fSopenharmony_ci    auto infos = FullImeInfoManager::GetInstance().Get(userId);
80322736c2fSopenharmony_ci    auto it = std::find_if(infos.begin(), infos.end(),
80422736c2fSopenharmony_ci        [&defaultIme](const FullImeInfo &info) { return info.prop.name == defaultIme->name; });
80522736c2fSopenharmony_ci    if (it != infos.end()) {
80622736c2fSopenharmony_ci        prop = std::make_shared<Property>((*it).prop);
80722736c2fSopenharmony_ci        prop->id = defaultIme->id;
80822736c2fSopenharmony_ci        return ErrorCode::NO_ERROR;
80922736c2fSopenharmony_ci    }
81022736c2fSopenharmony_ci
81122736c2fSopenharmony_ci    IMSA_HILOGD("%{public}d get %{public}s form bms.", userId, defaultIme->name.c_str());
81222736c2fSopenharmony_ci    if (isBrief) {
81322736c2fSopenharmony_ci        IMSA_HILOGD("get brief info.");
81422736c2fSopenharmony_ci        if (prop == nullptr) {
81522736c2fSopenharmony_ci            prop = std::make_shared<Property>();
81622736c2fSopenharmony_ci        }
81722736c2fSopenharmony_ci        prop->name = defaultIme->name;
81822736c2fSopenharmony_ci        prop->id = defaultIme->id;
81922736c2fSopenharmony_ci        return ErrorCode::NO_ERROR;
82022736c2fSopenharmony_ci    }
82122736c2fSopenharmony_ci    prop = GetImeProperty(userId, defaultIme->name, defaultIme->id);
82222736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
82322736c2fSopenharmony_ci}
82422736c2fSopenharmony_ci
82522736c2fSopenharmony_cistd::shared_ptr<ImeInfo> ImeInfoInquirer::GetDefaultImeInfo(int32_t userId)
82622736c2fSopenharmony_ci{
82722736c2fSopenharmony_ci    auto defaultIme = GetDefaultImeCfgProp();
82822736c2fSopenharmony_ci    if (defaultIme == nullptr) {
82922736c2fSopenharmony_ci        IMSA_HILOGE("defaultIme is nullptr!");
83022736c2fSopenharmony_ci        return nullptr;
83122736c2fSopenharmony_ci    }
83222736c2fSopenharmony_ci    auto info = GetImeInfo(userId, defaultIme->name, "");
83322736c2fSopenharmony_ci    if (info == nullptr) {
83422736c2fSopenharmony_ci        IMSA_HILOGE("userId: %{public}d, bundleName: %{public}s getImeInfoFromBundleMgr failed!", userId,
83522736c2fSopenharmony_ci            defaultIme->name.c_str());
83622736c2fSopenharmony_ci        return nullptr;
83722736c2fSopenharmony_ci    }
83822736c2fSopenharmony_ci    if (!info->isNewIme) {
83922736c2fSopenharmony_ci        info->prop.id = defaultIme->id;
84022736c2fSopenharmony_ci        auto it = std::find_if(info->subProps.begin(), info->subProps.end(),
84122736c2fSopenharmony_ci            [defaultIme](const SubProperty &subProp) { return subProp.id == defaultIme->id; });
84222736c2fSopenharmony_ci        if (it != info->subProps.end()) {
84322736c2fSopenharmony_ci            info->subProp = *it;
84422736c2fSopenharmony_ci        }
84522736c2fSopenharmony_ci    }
84622736c2fSopenharmony_ci    return info;
84722736c2fSopenharmony_ci}
84822736c2fSopenharmony_ci
84922736c2fSopenharmony_ciImeNativeCfg ImeInfoInquirer::GetDefaultIme()
85022736c2fSopenharmony_ci{
85122736c2fSopenharmony_ci    ImeNativeCfg imeCfg;
85222736c2fSopenharmony_ci    if (!systemConfig_.defaultInputMethod.empty()) {
85322736c2fSopenharmony_ci        IMSA_HILOGI("defaultInputMethod: %{public}s.", systemConfig_.defaultInputMethod.c_str());
85422736c2fSopenharmony_ci        imeCfg.imeId = systemConfig_.defaultInputMethod;
85522736c2fSopenharmony_ci    } else {
85622736c2fSopenharmony_ci        char value[CONFIG_LEN] = { 0 };
85722736c2fSopenharmony_ci        auto code = GetParameter(DEFAULT_IME_KEY, "", value, CONFIG_LEN);
85822736c2fSopenharmony_ci        imeCfg.imeId = code > 0 ? value : "";
85922736c2fSopenharmony_ci    }
86022736c2fSopenharmony_ci    auto pos = imeCfg.imeId.find('/');
86122736c2fSopenharmony_ci    if (pos == std::string::npos || pos + 1 >= imeCfg.imeId.size()) {
86222736c2fSopenharmony_ci        IMSA_HILOGE("defaultIme: %{public}s is abnormal!", imeCfg.imeId.c_str());
86322736c2fSopenharmony_ci        return {};
86422736c2fSopenharmony_ci    }
86522736c2fSopenharmony_ci    imeCfg.bundleName = imeCfg.imeId.substr(0, pos);
86622736c2fSopenharmony_ci    imeCfg.extName = imeCfg.imeId.substr(pos + 1);
86722736c2fSopenharmony_ci    return imeCfg;
86822736c2fSopenharmony_ci}
86922736c2fSopenharmony_ci
87022736c2fSopenharmony_cisptr<OHOS::AppExecFwk::IBundleMgr> ImeInfoInquirer::GetBundleMgr()
87122736c2fSopenharmony_ci{
87222736c2fSopenharmony_ci    sptr<ISystemAbilityManager> systemAbilityManager =
87322736c2fSopenharmony_ci        SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
87422736c2fSopenharmony_ci    if (systemAbilityManager == nullptr) {
87522736c2fSopenharmony_ci        IMSA_HILOGE("systemAbilityManager is nullptr!");
87622736c2fSopenharmony_ci        return nullptr;
87722736c2fSopenharmony_ci    }
87822736c2fSopenharmony_ci    sptr<IRemoteObject> remoteObject = systemAbilityManager->GetSystemAbility(BUNDLE_MGR_SERVICE_SYS_ABILITY_ID);
87922736c2fSopenharmony_ci    if (remoteObject == nullptr) {
88022736c2fSopenharmony_ci        IMSA_HILOGE("remoteObject is nullptr!");
88122736c2fSopenharmony_ci        return nullptr;
88222736c2fSopenharmony_ci    }
88322736c2fSopenharmony_ci    return iface_cast<AppExecFwk::IBundleMgr>(remoteObject);
88422736c2fSopenharmony_ci}
88522736c2fSopenharmony_ci
88622736c2fSopenharmony_cistd::shared_ptr<SubProperty> ImeInfoInquirer::FindTargetSubtypeByCondition(const std::vector<SubProperty> &subProps,
88722736c2fSopenharmony_ci    const Condition &condition)
88822736c2fSopenharmony_ci{
88922736c2fSopenharmony_ci    auto it = subProps.end();
89022736c2fSopenharmony_ci    switch (condition) {
89122736c2fSopenharmony_ci        case Condition::UPPER: {
89222736c2fSopenharmony_ci            it = std::find_if(subProps.begin(), subProps.end(),
89322736c2fSopenharmony_ci                [](const SubProperty &subProp) { return subProp.mode == "upper"; });
89422736c2fSopenharmony_ci            break;
89522736c2fSopenharmony_ci        }
89622736c2fSopenharmony_ci        case Condition::LOWER: {
89722736c2fSopenharmony_ci            it = std::find_if(subProps.begin(), subProps.end(),
89822736c2fSopenharmony_ci                [](const SubProperty &subProp) { return subProp.mode == "lower"; });
89922736c2fSopenharmony_ci            break;
90022736c2fSopenharmony_ci        }
90122736c2fSopenharmony_ci        case Condition::ENGLISH: {
90222736c2fSopenharmony_ci            it = std::find_if(subProps.begin(), subProps.end(),
90322736c2fSopenharmony_ci                [](const SubProperty &subProp) { return subProp.language == "english" && subProp.mode == "lower"; });
90422736c2fSopenharmony_ci            break;
90522736c2fSopenharmony_ci        }
90622736c2fSopenharmony_ci        case Condition::CHINESE: {
90722736c2fSopenharmony_ci            it = std::find_if(subProps.begin(), subProps.end(),
90822736c2fSopenharmony_ci                [](const SubProperty &subProp) { return subProp.language == "chinese"; });
90922736c2fSopenharmony_ci            break;
91022736c2fSopenharmony_ci        }
91122736c2fSopenharmony_ci        default: {
91222736c2fSopenharmony_ci            break;
91322736c2fSopenharmony_ci        }
91422736c2fSopenharmony_ci    }
91522736c2fSopenharmony_ci    if (it == subProps.end()) {
91622736c2fSopenharmony_ci        return nullptr;
91722736c2fSopenharmony_ci    }
91822736c2fSopenharmony_ci    return std::make_shared<SubProperty>(*it);
91922736c2fSopenharmony_ci}
92022736c2fSopenharmony_ci
92122736c2fSopenharmony_cibool ImeInfoInquirer::ParseSubtypeProfile(const std::vector<std::string> &profiles, SubtypeCfg &subtypeCfg)
92222736c2fSopenharmony_ci{
92322736c2fSopenharmony_ci    if (profiles.empty() || profiles.size() != SUBTYPE_PROFILE_NUM) {
92422736c2fSopenharmony_ci        IMSA_HILOGE("profiles size: %{public}zu!", profiles.size());
92522736c2fSopenharmony_ci        return false;
92622736c2fSopenharmony_ci    }
92722736c2fSopenharmony_ci    return subtypeCfg.Unmarshall(profiles[0]);
92822736c2fSopenharmony_ci}
92922736c2fSopenharmony_ci
93022736c2fSopenharmony_cistd::shared_ptr<Property> ImeInfoInquirer::GetDefaultImeCfgProp()
93122736c2fSopenharmony_ci{
93222736c2fSopenharmony_ci    auto ime = GetDefaultIme();
93322736c2fSopenharmony_ci    if (ime.bundleName.empty() || ime.extName.empty()) {
93422736c2fSopenharmony_ci        IMSA_HILOGE("defaultIme is abnormal!");
93522736c2fSopenharmony_ci        return nullptr;
93622736c2fSopenharmony_ci    }
93722736c2fSopenharmony_ci    auto defaultIme = std::make_shared<Property>();
93822736c2fSopenharmony_ci    defaultIme->name = ime.bundleName;
93922736c2fSopenharmony_ci    defaultIme->id = ime.extName;
94022736c2fSopenharmony_ci    return defaultIme;
94122736c2fSopenharmony_ci}
94222736c2fSopenharmony_ci
94322736c2fSopenharmony_cistd::shared_ptr<ResourceManager> ImeInfoInquirer::GetResMgr(const std::string &resourcePath)
94422736c2fSopenharmony_ci{
94522736c2fSopenharmony_ci    if (resourcePath.empty()) {
94622736c2fSopenharmony_ci        IMSA_HILOGE("resourcePath is empty!");
94722736c2fSopenharmony_ci        return nullptr;
94822736c2fSopenharmony_ci    }
94922736c2fSopenharmony_ci    std::shared_ptr<ResourceManager> resMgr(CreateResourceManager());
95022736c2fSopenharmony_ci    if (resMgr == nullptr) {
95122736c2fSopenharmony_ci        IMSA_HILOGE("resMgr is nullptr!");
95222736c2fSopenharmony_ci        return nullptr;
95322736c2fSopenharmony_ci    }
95422736c2fSopenharmony_ci    resMgr->AddResource(resourcePath.c_str());
95522736c2fSopenharmony_ci    std::unique_ptr<ResConfig> resConfig(CreateResConfig());
95622736c2fSopenharmony_ci    if (resConfig == nullptr) {
95722736c2fSopenharmony_ci        IMSA_HILOGE("resConfig is nullptr!");
95822736c2fSopenharmony_ci        return nullptr;
95922736c2fSopenharmony_ci    }
96022736c2fSopenharmony_ci    std::map<std::string, std::string> configs;
96122736c2fSopenharmony_ci    OHOS::Global::I18n::LocaleInfo locale(Global::I18n::LocaleConfig::GetSystemLocale(), configs);
96222736c2fSopenharmony_ci    resConfig->SetLocaleInfo(locale.GetLanguage().c_str(), locale.GetScript().c_str(), locale.GetRegion().c_str());
96322736c2fSopenharmony_ci    resMgr->UpdateResConfig(*resConfig);
96422736c2fSopenharmony_ci    return resMgr;
96522736c2fSopenharmony_ci}
96622736c2fSopenharmony_ci
96722736c2fSopenharmony_ciint32_t ImeInfoInquirer::QueryFullImeInfo(std::vector<std::pair<int32_t, std::vector<FullImeInfo>>> &fullImeInfos)
96822736c2fSopenharmony_ci{
96922736c2fSopenharmony_ci    auto userIds = OsAccountAdapter::QueryActiveOsAccountIds();
97022736c2fSopenharmony_ci    if (userIds.empty()) {
97122736c2fSopenharmony_ci        return ErrorCode::ERROR_OS_ACCOUNT;
97222736c2fSopenharmony_ci    }
97322736c2fSopenharmony_ci    for (auto &userId : userIds) {
97422736c2fSopenharmony_ci        std::vector<FullImeInfo> infos;
97522736c2fSopenharmony_ci        auto errNo = QueryFullImeInfo(userId, infos);
97622736c2fSopenharmony_ci        if (errNo != ErrorCode::NO_ERROR) {
97722736c2fSopenharmony_ci            continue;
97822736c2fSopenharmony_ci        }
97922736c2fSopenharmony_ci        fullImeInfos.emplace_back(userId, infos);
98022736c2fSopenharmony_ci    }
98122736c2fSopenharmony_ci    if (fullImeInfos.empty()) {
98222736c2fSopenharmony_ci        return ErrorCode::ERROR_PACKAGE_MANAGER;
98322736c2fSopenharmony_ci    }
98422736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
98522736c2fSopenharmony_ci}
98622736c2fSopenharmony_ci
98722736c2fSopenharmony_ciint32_t ImeInfoInquirer::QueryFullImeInfo(int32_t userId, std::vector<FullImeInfo> &imeInfo)
98822736c2fSopenharmony_ci{
98922736c2fSopenharmony_ci    std::vector<ExtensionAbilityInfo> extInfos;
99022736c2fSopenharmony_ci    auto ret = ImeInfoInquirer::GetInstance().QueryImeExtInfos(userId, extInfos);
99122736c2fSopenharmony_ci    if (!ret || extInfos.empty()) {
99222736c2fSopenharmony_ci        IMSA_HILOGE("%{public}d QueryImeExtInfos failed!", userId);
99322736c2fSopenharmony_ci        return ErrorCode::ERROR_PACKAGE_MANAGER;
99422736c2fSopenharmony_ci    }
99522736c2fSopenharmony_ci    std::map<std::string, std::vector<ExtensionAbilityInfo>> tempExtInfos;
99622736c2fSopenharmony_ci    for (const auto &extInfo : extInfos) {
99722736c2fSopenharmony_ci        if (IsTempInputMethod(extInfo)) {
99822736c2fSopenharmony_ci            continue;
99922736c2fSopenharmony_ci        }
100022736c2fSopenharmony_ci        auto it = tempExtInfos.find(extInfo.bundleName);
100122736c2fSopenharmony_ci        if (it != tempExtInfos.end()) {
100222736c2fSopenharmony_ci            it->second.push_back(extInfo);
100322736c2fSopenharmony_ci            continue;
100422736c2fSopenharmony_ci        }
100522736c2fSopenharmony_ci        tempExtInfos.insert({ extInfo.bundleName, { extInfo } });
100622736c2fSopenharmony_ci    }
100722736c2fSopenharmony_ci
100822736c2fSopenharmony_ci    for (const auto &extInfo : tempExtInfos) {
100922736c2fSopenharmony_ci        FullImeInfo info;
101022736c2fSopenharmony_ci        auto errNo = GetFullImeInfo(userId, extInfo.second, info);
101122736c2fSopenharmony_ci        if (errNo != ErrorCode::NO_ERROR) {
101222736c2fSopenharmony_ci            return errNo;
101322736c2fSopenharmony_ci        }
101422736c2fSopenharmony_ci        imeInfo.push_back(info);
101522736c2fSopenharmony_ci    }
101622736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
101722736c2fSopenharmony_ci}
101822736c2fSopenharmony_ci
101922736c2fSopenharmony_ciint32_t ImeInfoInquirer::GetFullImeInfo(int32_t userId, const std::string &bundleName, FullImeInfo &imeInfo)
102022736c2fSopenharmony_ci{
102122736c2fSopenharmony_ci    std::vector<ExtensionAbilityInfo> extInfos;
102222736c2fSopenharmony_ci    auto ret = ImeInfoInquirer::GetInstance().QueryImeExtInfos(userId, extInfos);
102322736c2fSopenharmony_ci    if (!ret || extInfos.empty()) {
102422736c2fSopenharmony_ci        return ErrorCode::ERROR_PACKAGE_MANAGER;
102522736c2fSopenharmony_ci    }
102622736c2fSopenharmony_ci    std::vector<ExtensionAbilityInfo> tempExtInfos;
102722736c2fSopenharmony_ci    for (const auto &extInfo : extInfos) {
102822736c2fSopenharmony_ci        if (IsTempInputMethod(extInfo)) {
102922736c2fSopenharmony_ci            continue;
103022736c2fSopenharmony_ci        }
103122736c2fSopenharmony_ci        if (extInfo.bundleName == bundleName) {
103222736c2fSopenharmony_ci            tempExtInfos.push_back(extInfo);
103322736c2fSopenharmony_ci        }
103422736c2fSopenharmony_ci    }
103522736c2fSopenharmony_ci    return GetFullImeInfo(userId, tempExtInfos, imeInfo);
103622736c2fSopenharmony_ci}
103722736c2fSopenharmony_ci
103822736c2fSopenharmony_ciint32_t ImeInfoInquirer::GetFullImeInfo(
103922736c2fSopenharmony_ci    int32_t userId, const std::vector<OHOS::AppExecFwk::ExtensionAbilityInfo> &extInfos, FullImeInfo &imeInfo)
104022736c2fSopenharmony_ci{
104122736c2fSopenharmony_ci    if (extInfos.empty()) {
104222736c2fSopenharmony_ci        return ErrorCode::ERROR_PACKAGE_MANAGER;
104322736c2fSopenharmony_ci    }
104422736c2fSopenharmony_ci    imeInfo.isNewIme = IsNewExtInfos(extInfos);
104522736c2fSopenharmony_ci    auto ret = imeInfo.isNewIme ? ListInputMethodSubtype(userId, extInfos[0], imeInfo.subProps)
104622736c2fSopenharmony_ci                        : ListInputMethodSubtype(userId, extInfos, imeInfo.subProps);
104722736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR) {
104822736c2fSopenharmony_ci        IMSA_HILOGE("[%{public}d,%{public}s] list Subtype failed!", userId, extInfos[0].bundleName.c_str());
104922736c2fSopenharmony_ci        return ret;
105022736c2fSopenharmony_ci    }
105122736c2fSopenharmony_ci    imeInfo.tokenId = extInfos[0].applicationInfo.accessTokenId;
105222736c2fSopenharmony_ci    imeInfo.prop.name = extInfos[0].bundleName;
105322736c2fSopenharmony_ci    imeInfo.prop.id = extInfos[0].name;
105422736c2fSopenharmony_ci    imeInfo.prop.label = GetTargetString(extInfos[0], ImeTargetString::LABEL, userId);
105522736c2fSopenharmony_ci    imeInfo.prop.labelId = extInfos[0].applicationInfo.labelId;
105622736c2fSopenharmony_ci    imeInfo.prop.iconId = extInfos[0].applicationInfo.iconId;
105722736c2fSopenharmony_ci    BundleInfo bundleInfo;
105822736c2fSopenharmony_ci    if (GetBundleInfoByBundleName(userId, imeInfo.prop.name, bundleInfo)) {
105922736c2fSopenharmony_ci        imeInfo.appId = bundleInfo.signatureInfo.appIdentifier;
106022736c2fSopenharmony_ci        imeInfo.versionCode = bundleInfo.versionCode;
106122736c2fSopenharmony_ci    }
106222736c2fSopenharmony_ci    return ErrorCode::NO_ERROR;
106322736c2fSopenharmony_ci}
106422736c2fSopenharmony_ci
106522736c2fSopenharmony_cibool ImeInfoInquirer::IsInputMethod(int32_t userId, const std::string &bundleName)
106622736c2fSopenharmony_ci{
106722736c2fSopenharmony_ci    auto bmg = GetBundleMgr();
106822736c2fSopenharmony_ci    if (bmg == nullptr) {
106922736c2fSopenharmony_ci        return false;
107022736c2fSopenharmony_ci    }
107122736c2fSopenharmony_ci    BundleInfo bundleInfo;
107222736c2fSopenharmony_ci    auto ret = bmg->GetBundleInfo(bundleName, BundleFlag::GET_BUNDLE_WITH_EXTENSION_INFO, bundleInfo, userId);
107322736c2fSopenharmony_ci    if (!ret) {
107422736c2fSopenharmony_ci        return false;
107522736c2fSopenharmony_ci    }
107622736c2fSopenharmony_ci    for (const auto &extInfo : bundleInfo.extensionInfos) {
107722736c2fSopenharmony_ci        if (extInfo.type == ExtensionAbilityType::INPUTMETHOD) {
107822736c2fSopenharmony_ci            return true;
107922736c2fSopenharmony_ci        }
108022736c2fSopenharmony_ci    }
108122736c2fSopenharmony_ci    return false;
108222736c2fSopenharmony_ci}
108322736c2fSopenharmony_ci
108422736c2fSopenharmony_cibool ImeInfoInquirer::IsTempInputMethod(const ExtensionAbilityInfo &extInfo)
108522736c2fSopenharmony_ci{
108622736c2fSopenharmony_ci    auto iter = std::find_if(extInfo.metadata.begin(), extInfo.metadata.end(),
108722736c2fSopenharmony_ci        [](const Metadata &metadata) {
108822736c2fSopenharmony_ci            return metadata.name == TEMPORARY_INPUT_METHOD_METADATA_NAME;
108922736c2fSopenharmony_ci        });
109022736c2fSopenharmony_ci    return iter != extInfo.metadata.end();
109122736c2fSopenharmony_ci}
109222736c2fSopenharmony_ci
109322736c2fSopenharmony_cistd::vector<std::string> ImeInfoInquirer::GetRunningIme(int32_t userId)
109422736c2fSopenharmony_ci{
109522736c2fSopenharmony_ci    std::vector<std::string> bundleNames;
109622736c2fSopenharmony_ci    std::vector<RunningProcessInfo> infos;
109722736c2fSopenharmony_ci    AppMgrClient client;
109822736c2fSopenharmony_ci    auto ret = client.GetProcessRunningInfosByUserId(infos, userId);
109922736c2fSopenharmony_ci    if (ret != ErrorCode::NO_ERROR) {
110022736c2fSopenharmony_ci        IMSA_HILOGE("GetAllRunningProcesses failed, ret: %{public}d!", ret);
110122736c2fSopenharmony_ci        return bundleNames;
110222736c2fSopenharmony_ci    }
110322736c2fSopenharmony_ci    for (const auto &info : infos) {
110422736c2fSopenharmony_ci        if (info.extensionType_ == ExtensionAbilityType::INPUTMETHOD && !info.bundleNames.empty()) {
110522736c2fSopenharmony_ci            bundleNames.push_back(info.bundleNames[0]);
110622736c2fSopenharmony_ci        }
110722736c2fSopenharmony_ci    }
110822736c2fSopenharmony_ci    return bundleNames;
110922736c2fSopenharmony_ci}
111022736c2fSopenharmony_ci
111122736c2fSopenharmony_cibool ImeInfoInquirer::IsDefaultImeSet(int32_t userId)
111222736c2fSopenharmony_ci{
111322736c2fSopenharmony_ci    return ImeCfgManager::GetInstance().IsDefaultImeSet(userId);
111422736c2fSopenharmony_ci}
111522736c2fSopenharmony_ci
111622736c2fSopenharmony_cibool ImeInfoInquirer::IsRunningIme(int32_t userId, const std::string &bundleName)
111722736c2fSopenharmony_ci{
111822736c2fSopenharmony_ci    auto bundleNames = GetRunningIme(userId);
111922736c2fSopenharmony_ci    auto it = std::find_if(bundleNames.begin(), bundleNames.end(),
112022736c2fSopenharmony_ci        [&bundleName](const std::string &bundleNameTemp) { return bundleName == bundleNameTemp; });
112122736c2fSopenharmony_ci    return it != bundleNames.end();
112222736c2fSopenharmony_ci}
112322736c2fSopenharmony_ci
112422736c2fSopenharmony_cibool ImeInfoInquirer::GetImeAppId(int32_t userId, const std::string &bundleName, std::string &appId)
112522736c2fSopenharmony_ci{
112622736c2fSopenharmony_ci    FullImeInfo imeInfo;
112722736c2fSopenharmony_ci    if (FullImeInfoManager::GetInstance().Get(bundleName, userId, imeInfo) && !imeInfo.appId.empty()) {
112822736c2fSopenharmony_ci        appId = imeInfo.appId;
112922736c2fSopenharmony_ci        return true;
113022736c2fSopenharmony_ci    }
113122736c2fSopenharmony_ci    BundleInfo bundleInfo;
113222736c2fSopenharmony_ci    if (!GetBundleInfoByBundleName(userId, bundleName, bundleInfo)) {
113322736c2fSopenharmony_ci        return false;
113422736c2fSopenharmony_ci    }
113522736c2fSopenharmony_ci    appId = bundleInfo.signatureInfo.appIdentifier;
113622736c2fSopenharmony_ci    return !appId.empty();
113722736c2fSopenharmony_ci}
113822736c2fSopenharmony_ci
113922736c2fSopenharmony_cibool ImeInfoInquirer::GetImeVersionCode(int32_t userId, const std::string &bundleName, uint32_t &versionCode)
114022736c2fSopenharmony_ci{
114122736c2fSopenharmony_ci    FullImeInfo imeInfo;
114222736c2fSopenharmony_ci    if (FullImeInfoManager::GetInstance().Get(bundleName, userId, imeInfo)) {
114322736c2fSopenharmony_ci        versionCode = imeInfo.versionCode;
114422736c2fSopenharmony_ci        return true;
114522736c2fSopenharmony_ci    }
114622736c2fSopenharmony_ci    BundleInfo bundleInfo;
114722736c2fSopenharmony_ci    if (!GetBundleInfoByBundleName(userId, bundleName, bundleInfo)) {
114822736c2fSopenharmony_ci        return false;
114922736c2fSopenharmony_ci    }
115022736c2fSopenharmony_ci    versionCode = bundleInfo.versionCode;
115122736c2fSopenharmony_ci    return true;
115222736c2fSopenharmony_ci}
115322736c2fSopenharmony_ci
115422736c2fSopenharmony_cibool ImeInfoInquirer::GetBundleInfoByBundleName(
115522736c2fSopenharmony_ci    int32_t userId, const std::string &bundleName, AppExecFwk::BundleInfo &bundleInfo)
115622736c2fSopenharmony_ci{
115722736c2fSopenharmony_ci    auto bundleMgr = GetBundleMgr();
115822736c2fSopenharmony_ci    if (bundleMgr == nullptr) {
115922736c2fSopenharmony_ci        IMSA_HILOGE("failed to get bundleMgr!");
116022736c2fSopenharmony_ci        return false;
116122736c2fSopenharmony_ci    }
116222736c2fSopenharmony_ci    auto ret = bundleMgr->GetBundleInfo(
116322736c2fSopenharmony_ci        bundleName, static_cast<int32_t>(GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_SIGNATURE_INFO), bundleInfo, userId);
116422736c2fSopenharmony_ci    if (!ret) {
116522736c2fSopenharmony_ci        IMSA_HILOGE("failed to get bundle info");
116622736c2fSopenharmony_ci        return false;
116722736c2fSopenharmony_ci    }
116822736c2fSopenharmony_ci    return true;
116922736c2fSopenharmony_ci}
117022736c2fSopenharmony_ci
117122736c2fSopenharmony_cistd::string ImeInfoInquirer::GetTargetString(
117222736c2fSopenharmony_ci    const AppExecFwk::ExtensionAbilityInfo &extension, ImeTargetString target, int32_t userId)
117322736c2fSopenharmony_ci{
117422736c2fSopenharmony_ci    if (target == ImeTargetString::LABEL) {
117522736c2fSopenharmony_ci        if (extension.labelId != DEFAULT_BMS_VALUE) {
117622736c2fSopenharmony_ci            return GetStringById(extension.bundleName, extension.moduleName, extension.labelId, userId);
117722736c2fSopenharmony_ci        }
117822736c2fSopenharmony_ci        IMSA_HILOGD("Extension label is empty, get application label");
117922736c2fSopenharmony_ci        return GetStringById(extension.bundleName, extension.applicationInfo.labelResource.moduleName,
118022736c2fSopenharmony_ci            extension.applicationInfo.labelResource.id, userId);
118122736c2fSopenharmony_ci    }
118222736c2fSopenharmony_ci    if (target == ImeTargetString::DESCRIPTION) {
118322736c2fSopenharmony_ci        if (extension.descriptionId != DEFAULT_BMS_VALUE) {
118422736c2fSopenharmony_ci            return GetStringById(extension.bundleName, extension.moduleName, extension.descriptionId, userId);
118522736c2fSopenharmony_ci        }
118622736c2fSopenharmony_ci        IMSA_HILOGD("extension description is empty, get application description");
118722736c2fSopenharmony_ci        return GetStringById(extension.bundleName, extension.applicationInfo.descriptionResource.moduleName,
118822736c2fSopenharmony_ci            extension.applicationInfo.descriptionResource.id, userId);
118922736c2fSopenharmony_ci    }
119022736c2fSopenharmony_ci    IMSA_HILOGD("No match target string");
119122736c2fSopenharmony_ci    return "";
119222736c2fSopenharmony_ci}
119322736c2fSopenharmony_ci} // namespace MiscServices
119422736c2fSopenharmony_ci} // namespace OHOS