1 /*
2  * Copyright (C) 2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 #define private public
16 #define protected public
17 #include "full_ime_info_manager.h"
18 #include "ime_cfg_manager.h"
19 #include "ime_info_inquirer.h"
20 #include "input_method_controller.h"
21 #include "input_method_system_ability.h"
22 #include "peruser_session.h"
23 #include "wms_connection_observer.h"
24 #undef private
25 #include <gtest/gtest.h>
26 #include <sys/time.h>
27 #include <unistd.h>
28 
29 #include <string>
30 #include <vector>
31 
32 #include "application_info.h"
33 #include "global.h"
34 #include "i_input_method_agent.h"
35 #include "i_input_method_core.h"
36 #include "ime_cfg_manager.h"
37 #include "input_method_agent_proxy.h"
38 #include "input_method_agent_stub.h"
39 #include "input_method_core_stub.h"
40 #include "keyboard_event.h"
41 #include "os_account_manager.h"
42 #include "tdd_util.h"
43 #include "user_session_manager.h"
44 
45 using namespace testing::ext;
46 namespace OHOS {
47 namespace MiscServices {
48 using namespace AppExecFwk;
49 class InputMethodPrivateMemberTest : public testing::Test {
50 public:
51     static void SetUpTestCase(void);
52     static void TearDownTestCase(void);
53     void SetUp();
54     void TearDown();
55     static sptr<InputMethodSystemAbility> service_;
56 };
57 constexpr std::int32_t MAIN_USER_ID = 100;
SetUpTestCase(void)58 void InputMethodPrivateMemberTest::SetUpTestCase(void)
59 {
60     IMSA_HILOGI("InputMethodPrivateMemberTest::SetUpTestCase");
61     service_ = new (std::nothrow) InputMethodSystemAbility();
62     if (service_ == nullptr) {
63         return;
64     }
65     service_->OnStart();
66 }
67 
TearDownTestCase(void)68 void InputMethodPrivateMemberTest::TearDownTestCase(void)
69 {
70     service_->OnStop();
71     IMSA_HILOGI("InputMethodPrivateMemberTest::TearDownTestCase");
72 }
73 
SetUp(void)74 void InputMethodPrivateMemberTest::SetUp(void)
75 {
76     IMSA_HILOGI("InputMethodPrivateMemberTest::SetUp");
77     ImeCfgManager::GetInstance().imeConfigs_.clear();
78     FullImeInfoManager::GetInstance().fullImeInfos_.clear();
79     service_->userId_ = MAIN_USER_ID;
80 }
81 
TearDown(void)82 void InputMethodPrivateMemberTest::TearDown(void)
83 {
84     IMSA_HILOGI("InputMethodPrivateMemberTest::TearDown");
85     ImeCfgManager::GetInstance().imeConfigs_.clear();
86     FullImeInfoManager::GetInstance().fullImeInfos_.clear();
87 }
88 sptr<InputMethodSystemAbility> InputMethodPrivateMemberTest::service_;
89 
90 /**
91 * @tc.name: SA_TestOnStart
92 * @tc.desc: SA OnStart.
93 * @tc.type: FUNC
94 * @tc.require:
95 */
96 HWTEST_F(InputMethodPrivateMemberTest, SA_TestOnStart, TestSize.Level0)
97 {
98     InputMethodSystemAbility ability;
99     ability.state_ = ServiceRunningState::STATE_RUNNING;
100     ability.OnStart();
101     EXPECT_EQ(ability.identityChecker_, nullptr);
102 }
103 
104 /**
105 * @tc.name: SA_GetExtends
106 * @tc.desc: SA GetExtends.
107 * @tc.type: FUNC
108 * @tc.require: issuesI640YZ
109 */
110 HWTEST_F(InputMethodPrivateMemberTest, SA_GetExtends, TestSize.Level0)
111 {
112     constexpr int32_t metaDataNums = 5;
113     ImeInfoInquirer inquirer;
114     std::vector<Metadata> metaData;
115     Metadata metadata[metaDataNums] = { { "language", "english", "" }, { "mode", "mode", "" },
116         { "locale", "local", "" }, { "icon", "icon", "" }, { "", "", "" } };
117     for (auto const &data : metadata) {
118         metaData.emplace_back(data);
119     }
120     auto subProperty = inquirer.GetExtends(metaData);
121     EXPECT_EQ(subProperty.language, "english");
122     EXPECT_EQ(subProperty.mode, "mode");
123     EXPECT_EQ(subProperty.locale, "local");
124     EXPECT_EQ(subProperty.icon, "icon");
125 }
126 
127 /**
128 * @tc.name: SA_TestOnUserStarted
129 * @tc.desc: SA_TestOnUserStarted.
130 * @tc.type: FUNC
131 * @tc.require:
132 */
133 HWTEST_F(InputMethodPrivateMemberTest, SA_TestOnUserStarted, TestSize.Level0)
134 {
135     // isScbEnable_ is true
136     service_->isScbEnable_ = true;
137     MessageParcel *parcel = nullptr;
138     auto msg = std::make_shared<Message>(MessageID::MSG_ID_USER_START, parcel);
139     auto ret = service_->OnUserStarted(msg.get());
140     EXPECT_EQ(ret, ErrorCode::ERROR_NULL_POINTER);
141 
142     // msg is nullptr
143     service_->isScbEnable_ = false;
144     ret = service_->OnUserStarted(msg.get());
145     EXPECT_EQ(ret, ErrorCode::ERROR_NULL_POINTER);
146 
147     // userId is same
148     service_->userId_ = 50;
149     MessageParcel *parcel1 = new MessageParcel();
150     parcel1->WriteInt32(50);
151     auto msg1 = std::make_shared<Message>(MessageID::MSG_ID_USER_START, parcel1);
152     ret = service_->OnUserStarted(msg1.get());
153     EXPECT_EQ(ret, ErrorCode::NO_ERROR);
154 
155     // start ime
156     WmsConnectionObserver observer(nullptr);
157     observer.OnConnected(60, 0);
158     // imeStarting_ is true
159     IMSA_HILOGI("InputMethodPrivateMemberTest::imeStarting_ is true");
160     service_->userId_ = 50;
161     MessageParcel *parcel2 = new MessageParcel();
162     parcel2->WriteInt32(60);
163     auto msg2 = std::make_shared<Message>(MessageID::MSG_ID_USER_START, parcel2);
164     ret = service_->OnUserStarted(msg2.get());
165     EXPECT_EQ(ret, ErrorCode::NO_ERROR);
166     // imeStarting_ is false
167     IMSA_HILOGI("InputMethodPrivateMemberTest::imeStarting_ is false");
168     service_->userId_ = 50;
169     MessageParcel *parcel3 = new MessageParcel();
170     observer.OnConnected(333, 0);
171     parcel3->WriteInt32(333);
172     auto msg3 = std::make_shared<Message>(MessageID::MSG_ID_USER_START, parcel3);
173     ret = service_->OnUserStarted(msg3.get());
174     EXPECT_EQ(ret, ErrorCode::NO_ERROR);
175 }
176 
177 /**
178 * @tc.name: SA_TestOnUserRemoved
179 * @tc.desc: SA_TestOnUserRemoved.
180 * @tc.type: FUNC
181 * @tc.require:
182 */
183 HWTEST_F(InputMethodPrivateMemberTest, SA_TestOnUserRemoved, TestSize.Level0)
184 {
185     // msg is nullptr
186     auto *msg = new Message(MessageID::MSG_ID_USER_REMOVED, nullptr);
187     auto ret = service_->OnUserRemoved(msg);
188     EXPECT_EQ(ret, ErrorCode::ERROR_NULL_POINTER);
189     MessageHandler::Instance()->SendMessage(msg);
190 
191     // move userId
192     MessageParcel *parcel1 = new MessageParcel();
193     parcel1->WriteInt32(60);
194     auto msg1 = std::make_shared<Message>(MessageID::MSG_ID_USER_REMOVED, parcel1);
195     auto ret1 = service_->OnUserRemoved(msg1.get());
196     EXPECT_EQ(ret1, ErrorCode::NO_ERROR);
197 }
198 
199 /**
200 * @tc.name: SA_ListInputMethodInfoWithInexistentUserId
201 * @tc.desc: SA ListInputMethodInfo With Inexistent UserId.
202 * @tc.type: FUNC
203 * @tc.require: issuesI669E8
204 */
205 HWTEST_F(InputMethodPrivateMemberTest, SA_ListInputMethodInfoWithInexistentUserId, TestSize.Level0)
206 {
207     ImeInfoInquirer inquirer;
208     constexpr int32_t userId = 1;
209     auto inputMethodInfos = inquirer.ListInputMethodInfo(userId);
210     EXPECT_TRUE(inputMethodInfos.empty());
211 }
212 
213 /**
214 * @tc.name: IMC_ListInputMethodCommonWithErrorStatus
215 * @tc.desc: IMC ListInputMethodCommon With Error Status.
216 * @tc.type: FUNC
217 * @tc.require: issuesI669E8
218 */
219 HWTEST_F(InputMethodPrivateMemberTest, IMC_ListInputMethodCommonWithErrorStatus, TestSize.Level0)
220 {
221     std::vector<Property> props;
222     auto ret = InputMethodController::GetInstance()->ListInputMethodCommon(static_cast<InputMethodStatus>(5), props);
223     EXPECT_EQ(ret, ErrorCode::ERROR_BAD_PARAMETERS);
224     EXPECT_TRUE(props.empty());
225 }
226 
227 /**
228  * @tc.name: PerUserSessionCoreOrAgentNullptr
229  * @tc.desc: Test PerUserSession with core nullptr.
230  * @tc.type: FUNC
231  * @tc.require: issuesI794QF
232  * @tc.author: Zhaolinglan
233  */
234 HWTEST_F(InputMethodPrivateMemberTest, PerUserSessionCoreOrAgentNullptr, TestSize.Level0)
235 {
236     IMSA_HILOGI("InputMethodPrivateMemberTest PerUserSessionCoreOrAgentNullptr TEST START");
237     auto userSession = std::make_shared<PerUserSession>(MAIN_USER_ID);
238     auto imc = InputMethodController::GetInstance();
239     int32_t ret = userSession->ShowKeyboard(imc->clientInfo_.client);
240     EXPECT_EQ(ret, ErrorCode::ERROR_CLIENT_NOT_FOUND);
241     ret = userSession->HideKeyboard(imc->clientInfo_.client);
242     EXPECT_EQ(ret, ErrorCode::ERROR_CLIENT_NOT_FOUND);
243     ret = userSession->InitInputControlChannel();
244     EXPECT_EQ(ret, ErrorCode::ERROR_IME_NOT_STARTED);
245     userSession->StopCurrentIme();
246     ret = userSession->SwitchSubtype({});
247     EXPECT_EQ(ret, ErrorCode::ERROR_IME_NOT_STARTED);
248 }
249 
250 /**
251  * @tc.name: PerUserSessionClientError
252  * @tc.desc: Test PerUserSession with client error.
253  * @tc.type: FUNC
254  * @tc.require: issuesI794QF
255  * @tc.author: Zhaolinglan
256  */
257 HWTEST_F(InputMethodPrivateMemberTest, PerUserSessionClientError, TestSize.Level0)
258 {
259     IMSA_HILOGI("InputMethodPrivateMemberTest PerUserSessionClientError TEST START");
260     auto userSession = std::make_shared<PerUserSession>(MAIN_USER_ID);
261     auto imc = InputMethodController::GetInstance();
262     sptr<InputMethodCoreStub> core = new InputMethodCoreStub();
263 
264     auto clientInfo = userSession->GetClientInfo(imc->clientInfo_.client->AsObject());
265     EXPECT_EQ(clientInfo, nullptr);
266 
267     userSession->SetCurrentClient(nullptr);
268     userSession->OnUnfocused(0, 0);
269     int32_t ret = userSession->OnHideCurrentInput();
270     EXPECT_EQ(ret, ErrorCode::ERROR_CLIENT_NOT_FOUND);
271     ret = userSession->OnShowCurrentInput();
272     EXPECT_EQ(ret, ErrorCode::ERROR_CLIENT_NOT_FOUND);
273 
274     userSession->SetCurrentClient(imc->clientInfo_.client);
275     ret = userSession->OnShowCurrentInput();
276     EXPECT_EQ(ret, ErrorCode::ERROR_CLIENT_NOT_FOUND);
277 }
278 
279 /**
280  * @tc.name: PerUserSessionParameterNullptr001
281  * @tc.desc: Test PerUserSession with parameter client nullptr.
282  * @tc.type: FUNC
283  * @tc.require: issuesI794QF
284  * @tc.author: Zhaolinglan
285  */
286 HWTEST_F(InputMethodPrivateMemberTest, PerUserSessionParameterNullptr001, TestSize.Level0)
287 {
288     IMSA_HILOGI("InputMethodPrivateMemberTest PerUserSessionParameterNullptr001 TEST START");
289     auto userSession = std::make_shared<PerUserSession>(MAIN_USER_ID);
290     sptr<IRemoteObject> agent = nullptr;
291     InputClientInfo clientInfo;
292     int32_t ret = userSession->OnStartInput(clientInfo, agent);
293     EXPECT_EQ(ret, ErrorCode::ERROR_CLIENT_NULL_POINTER);
294     ret = userSession->OnReleaseInput(nullptr);
295     EXPECT_EQ(ret, ErrorCode::ERROR_CLIENT_NULL_POINTER);
296     auto client = userSession->GetClientInfo(nullptr);
297     EXPECT_EQ(client, nullptr);
298 }
299 
300 /**
301  * @tc.name: PerUserSessionParameterNullptr003
302  * @tc.desc: Test PerUserSession with parameter nullptr.
303  * @tc.type: FUNC
304  * @tc.require: issuesI794QF
305  * @tc.author: Zhaolinglan
306  */
307 HWTEST_F(InputMethodPrivateMemberTest, PerUserSessionParameterNullptr003, TestSize.Level0)
308 {
309     IMSA_HILOGI("InputMethodPrivateMemberTest PerUserSessionParameterNullptr003 TEST START");
310     auto userSession = std::make_shared<PerUserSession>(MAIN_USER_ID);
311     sptr<InputMethodCoreStub> core = new InputMethodCoreStub();
312     userSession->OnClientDied(nullptr);
313     userSession->OnImeDied(nullptr, ImeType::IME);
314     bool isShowKeyboard = false;
315     userSession->UpdateClientInfo(nullptr, { { UpdateFlag::ISSHOWKEYBOARD, isShowKeyboard } });
316     int32_t ret = userSession->RemoveIme(nullptr, ImeType::IME);
317     EXPECT_EQ(ret, ErrorCode::ERROR_NULL_POINTER);
318 }
319 
320 /**
321  * @tc.name: SA_ImeCfgManagerTest_002
322  * @tc.desc: getImeCfg failed
323  * @tc.type: FUNC
324  * @tc.require:
325  * @tc.author: chenyu
326  */
327 HWTEST_F(InputMethodPrivateMemberTest, SA_ImeCfgManagerTest_002, TestSize.Level0)
328 {
329     IMSA_HILOGI("InputMethodPrivateMemberTest SA_ImeCfgManagerTest_002 TEST START");
330     ImeCfgManager cfgManager;
331     auto cfg = cfgManager.GetImeCfg(100);
332     EXPECT_TRUE(cfg.currentSubName.empty());
333     EXPECT_TRUE(cfg.currentIme.empty());
334 }
335 
336 /**
337  * @tc.name: SA_SwitchByCombinationKey_001
338  * @tc.desc: keycode = MMI::KeyEvent::KEYCODE_0
339  * @tc.type: FUNC
340  * @tc.require:
341  * @tc.author: chenyu
342  */
343 HWTEST_F(InputMethodPrivateMemberTest, SA_SwitchByCombinationKey_001, TestSize.Level0)
344 {
345     IMSA_HILOGI("InputMethodPrivateMemberTest SA_SwitchByCombinationKey_001 TEST START");
346     ImeCfgManager cfgManager;
347     auto ret = service_->SwitchByCombinationKey(0);
348     EXPECT_EQ(ret, ErrorCode::ERROR_EX_UNSUPPORTED_OPERATION);
349 }
350 
351 /**
352  * @tc.name: SA_SwitchByCombinationKey_002
353  * @tc.desc: SwitchLanguage()/SwitchMode():GetImeInfo failed
354  * @tc.type: FUNC
355  * @tc.require:
356  * @tc.author: chenyu
357  */
358 HWTEST_F(InputMethodPrivateMemberTest, SA_SwitchByCombinationKey_002, TestSize.Level0)
359 {
360     IMSA_HILOGI("InputMethodPrivateMemberTest SA_SwitchByCombinationKey_002 TEST START");
361     ImeCfgManager cfgManager;
362     auto ret = service_->SwitchByCombinationKey(KeyboardEvent::SHIFT_RIGHT_MASK);
363     EXPECT_EQ(ret, ErrorCode::ERROR_BAD_PARAMETERS);
364     ret = service_->SwitchByCombinationKey(KeyboardEvent::CAPS_MASK);
365     EXPECT_EQ(ret, ErrorCode::ERROR_BAD_PARAMETERS);
366 }
367 
368 /**
369  * @tc.name: SA_SwitchByCombinationKey_003
370  * @tc.desc: SwitchLanguage()/SwitchMode():is newIme
371  * @tc.type: FUNC
372  * @tc.require:
373  * @tc.author: chenyu
374  */
375 HWTEST_F(InputMethodPrivateMemberTest, SA_SwitchByCombinationKey_003, TestSize.Level0)
376 {
377     IMSA_HILOGI("InputMethodPrivateMemberTest SA_SwitchByCombinationKey_003 TEST START");
378     ImeCfgManager cfgManager;
379     FullImeInfo info;
380     info.isNewIme = true;
381     info.prop = { .name = "testBundleName" };
382     info.subProps = { { .id = "testSubName" } };
383     FullImeInfoManager::GetInstance().fullImeInfos_.insert({ MAIN_USER_ID, { info } });
384     ImeCfgManager::GetInstance().imeConfigs_.push_back({ MAIN_USER_ID, "testBundleName/testExtName", "testSubName",
385         false });
386     auto ret = service_->SwitchByCombinationKey(KeyboardEvent::SHIFT_RIGHT_MASK);
387     EXPECT_EQ(ret, ErrorCode::NO_ERROR);
388     ret = service_->SwitchByCombinationKey(KeyboardEvent::CAPS_MASK);
389     EXPECT_EQ(ret, ErrorCode::NO_ERROR);
390 }
391 
392 /**
393  * @tc.name: SA_SwitchByCombinationKey_004
394  * @tc.desc: SwitchLanguage():info.subProp.language == "French"
395  * @tc.type: FUNC
396  * @tc.require:
397  * @tc.author: chenyu
398  */
399 HWTEST_F(InputMethodPrivateMemberTest, SA_SwitchByCombinationKey_004, TestSize.Level0)
400 {
401     IMSA_HILOGI("InputMethodPrivateMemberTest SA_SwitchByCombinationKey_004 TEST START");
402     FullImeInfo info;
403     info.prop = { .name = "testBundleName", .id = "testExtName" };
404     info.subProps = { { .name = "testBundleName", .id = "testSubName", .language = "French" } };
405     FullImeInfoManager::GetInstance().fullImeInfos_.insert({ MAIN_USER_ID, { info } });
406     ImeCfgManager::GetInstance().imeConfigs_.push_back({ MAIN_USER_ID, "testBundleName/testExtName", "testSubName",
407         false });
408     auto ret = service_->SwitchByCombinationKey(KeyboardEvent::SHIFT_RIGHT_MASK);
409     EXPECT_EQ(ret, ErrorCode::NO_ERROR);
410 }
411 
412 /**
413  * @tc.name: SA_SwitchByCombinationKey_005
414  * @tc.desc: SwitchLanguage()/SwitchMode():FindTargetSubtypeByCondition failed
415  * @tc.type: FUNC
416  * @tc.require:
417  * @tc.author: chenyu
418  */
419 HWTEST_F(InputMethodPrivateMemberTest, SA_SwitchByCombinationKey_005, TestSize.Level0)
420 {
421     IMSA_HILOGI("InputMethodPrivateMemberTest SA_SwitchByCombinationKey_005 TEST START");
422     FullImeInfo info;
423     info.prop = { .name = "testBundleName", .id = "testExtName" };
424     info.subProps = { { .name = "testBundleName", .id = "testSubName", .mode = "upper", .language = "english" } };
425     FullImeInfoManager::GetInstance().fullImeInfos_.insert({ MAIN_USER_ID, { info } });
426     ImeCfgManager::GetInstance().imeConfigs_.push_back({ MAIN_USER_ID, "testBundleName/testExtName", "testSubName",
427         false });
428     auto ret = service_->SwitchByCombinationKey(KeyboardEvent::SHIFT_RIGHT_MASK);
429     EXPECT_EQ(ret, ErrorCode::ERROR_BAD_PARAMETERS);
430     ret = service_->SwitchByCombinationKey(KeyboardEvent::CAPS_MASK);
431     EXPECT_EQ(ret, ErrorCode::ERROR_BAD_PARAMETERS);
432 }
433 
434 /**
435  * @tc.name: SA_SwitchByCombinationKey_006
436  * @tc.desc: SwitchLanguage()/SwitchMode():StartInputService() failed
437  * @tc.type: FUNC
438  * @tc.require:
439  * @tc.author: chenyu
440  */
441 HWTEST_F(InputMethodPrivateMemberTest, SA_SwitchByCombinationKey_006, TestSize.Level0)
442 {
443     IMSA_HILOGI("InputMethodPrivateMemberTest SA_SwitchByCombinationKey_006 TEST START");
444     FullImeInfo info;
445     info.prop = { .name = "testBundleName", .id = "testExtName" };
446     info.subProps = { { .name = "testBundleName", .id = "testSubName", .mode = "upper", .language = "english" },
447         { .name = "testBundleName", .id = "testSubName1", .mode = "lower", .language = "chinese" } };
448     FullImeInfoManager::GetInstance().fullImeInfos_.insert({ MAIN_USER_ID, { info } });
449 
450     ImeCfgManager::GetInstance().imeConfigs_.push_back({ MAIN_USER_ID, "testBundleName/testExtName", "testSubName",
451         false});
452     // english->chinese
453     auto ret = service_->SwitchByCombinationKey(KeyboardEvent::SHIFT_RIGHT_MASK);
454     EXPECT_EQ(ret, ErrorCode::ERROR_IME_START_FAILED);
455     // lower->upper
456     ret = service_->SwitchByCombinationKey(KeyboardEvent::CAPS_MASK);
457     EXPECT_EQ(ret, ErrorCode::ERROR_IME_START_FAILED);
458 }
459 
460 /**
461  * @tc.name: SA_SwitchByCombinationKey_007
462  * @tc.desc: SwitchType():StartInputService() failed
463  * @tc.type: FUNC
464  * @tc.require:
465  * @tc.author: chenyu
466  */
467 HWTEST_F(InputMethodPrivateMemberTest, SA_SwitchByCombinationKey_007, TestSize.Level0)
468 {
469     IMSA_HILOGI("InputMethodPrivateMemberTest SA_SwitchByCombinationKey_007 TEST START");
470     auto userId = TddUtil::GetCurrentUserId();
471     service_->userId_ = userId;
472     std::vector<Property> props;
473     InputMethodController::GetInstance()->ListInputMethod(props);
474     if (props.size() == 1) {
475         auto ret = service_->SwitchByCombinationKey(KeyboardEvent::SHIFT_RIGHT_MASK | KeyboardEvent::CTRL_RIGHT_MASK);
476         EXPECT_EQ(ret, ErrorCode::NO_ERROR);
477     }
478 }
479 
480 /**
481  * @tc.name: SA_SwitchByCombinationKey_008
482  * @tc.desc: SwitchType():find_if failed
483  * @tc.type: FUNC
484  * @tc.require:
485  * @tc.author: chenyu
486  */
487 HWTEST_F(InputMethodPrivateMemberTest, SA_SwitchByCombinationKey_008, TestSize.Level0)
488 {
489     IMSA_HILOGI("InputMethodPrivateMemberTest SA_SwitchByCombinationKey_008 TEST START");
490     auto userId = TddUtil::GetCurrentUserId();
491     service_->userId_ = userId;
492     auto prop = InputMethodController::GetInstance()->GetCurrentInputMethod();
493     auto subProp = InputMethodController::GetInstance()->GetCurrentInputMethodSubtype();
494     ImeCfgManager::GetInstance().imeConfigs_.push_back({ userId, prop->name + "/" + prop->id, subProp->id, false });
495     std::vector<Property> props;
496     InputMethodController::GetInstance()->ListInputMethod(props);
497     if (props.size() == 1) {
498         auto ret = service_->SwitchByCombinationKey(KeyboardEvent::SHIFT_RIGHT_MASK | KeyboardEvent::CTRL_RIGHT_MASK);
499         EXPECT_EQ(ret, ErrorCode::NO_ERROR);
500     }
501 }
502 
503 /**
504  * @tc.name: SA_testReleaseInput_001
505  * @tc.desc: client is nullptr
506  * @tc.type: FUNC
507  * @tc.require:
508  * @tc.author: chenyu
509  */
510 HWTEST_F(InputMethodPrivateMemberTest, SA_testReleaseInput_001, TestSize.Level0)
511 {
512     IMSA_HILOGI("InputMethodPrivateMemberTest SA_testReleaseInput_001 TEST START");
513     auto ret = service_->ReleaseInput(nullptr);
514     EXPECT_EQ(ret, ErrorCode::ERROR_CLIENT_NULL_POINTER);
515 }
516 
517 /**
518  * @tc.name: III_TestGetCurrentInputMethodSubtype_001
519  * @tc.desc:
520  * @tc.type: FUNC
521  * @tc.require:
522  * @tc.author: chenyu
523  */
524 HWTEST_F(InputMethodPrivateMemberTest, III_TestGetCurrentSubtype_001, TestSize.Level0)
525 {
526     IMSA_HILOGI("InputMethodPrivateMemberTest III_TestGetCurrentInputMethodSubtype_001 TEST START");
527     // currentIme is empty
528     auto currentUserId = TddUtil::GetCurrentUserId();
529     auto subProp = ImeInfoInquirer::GetInstance().GetCurrentSubtype(currentUserId);
530     EXPECT_TRUE(subProp == nullptr);
531 
532     // subName is not find
533     auto currentProp = InputMethodController::GetInstance()->GetCurrentInputMethod();
534     ImeCfgManager::GetInstance().imeConfigs_.push_back(
535         { currentUserId, currentProp->name + "/" + currentProp->id, "tt", false });
536     subProp = ImeInfoInquirer::GetInstance().GetCurrentSubtype(currentUserId);
537     ASSERT_TRUE(subProp != nullptr);
538     EXPECT_TRUE(subProp->name == currentProp->name);
539 
540     // get correct subProp
541     auto currentSubProp = InputMethodController::GetInstance()->GetCurrentInputMethodSubtype();
542     ImeCfgManager::GetInstance().imeConfigs_.push_back(
543         { currentUserId, currentProp->name + "/" + currentProp->id, currentSubProp->id, false });
544     subProp = ImeInfoInquirer::GetInstance().GetCurrentSubtype(currentUserId);
545     ASSERT_TRUE(subProp != nullptr);
546     EXPECT_TRUE(subProp->id == currentSubProp->id);
547 }
548 
549 /**
550  * @tc.name: III_TestGetCurrentInputMethod_001
551  * @tc.desc:
552  * @tc.type: FUNC
553  * @tc.require:
554  * @tc.author: chenyu
555  */
556 HWTEST_F(InputMethodPrivateMemberTest, III_TestGetCurrentIme_001, TestSize.Level0)
557 {
558     IMSA_HILOGI("InputMethodPrivateMemberTest III_TestGetCurrentInputMethod_001 TEST START");
559     // currentIme is empty
560     auto currentUserId = TddUtil::GetCurrentUserId();
561     auto prop = ImeInfoInquirer::GetInstance().GetCurrentInputMethod(currentUserId);
562     EXPECT_TRUE(prop == nullptr);
563 
564     // get correct prop
565     auto currentProp = InputMethodController::GetInstance()->GetCurrentInputMethod();
566     ImeCfgManager::GetInstance().imeConfigs_.push_back(
567         { currentUserId, currentProp->name + "/" + currentProp->id, currentProp->id, false});
568     prop = ImeInfoInquirer::GetInstance().GetCurrentInputMethod(currentUserId);
569     ASSERT_TRUE(prop != nullptr);
570     EXPECT_TRUE(prop->id == currentProp->id);
571 }
572 
573 /**
574  * @tc.name: III_TestListEnabledInputMethod_001
575  * @tc.desc:
576  * @tc.type: FUNC
577  * @tc.require:
578  * @tc.author: chenyu
579  */
580 HWTEST_F(InputMethodPrivateMemberTest, III_TestListEnabledInputMethod_001, TestSize.Level0)
581 {
582     IMSA_HILOGI("InputMethodPrivateMemberTest III_TestListEnabledInputMethod_001 TEST START");
583     // currentIme is empty
584     std::vector<Property> props;
585     auto currentUserId = TddUtil::GetCurrentUserId();
586     auto ret = ImeInfoInquirer::GetInstance().ListEnabledInputMethod(currentUserId, props, false);
587     EXPECT_EQ(ret, ErrorCode::NO_ERROR);
588 }
589 
590 /**
591  * @tc.name: III_TestListCurrentInputMethodSubtype_001
592  * @tc.desc:
593  * @tc.type: FUNC
594  * @tc.require:
595  * @tc.author: chenyu
596  */
597 HWTEST_F(InputMethodPrivateMemberTest, III_TestListCurrentInputMethodSubtype_001, TestSize.Level0)
598 {
599     IMSA_HILOGI("InputMethodPrivateMemberTest III_TestListCurrentInputMethodSubtype_001 TEST START");
600     // currentIme is empty
601     std::vector<SubProperty> subProps;
602     auto currentUserId = TddUtil::GetCurrentUserId();
603     auto ret = ImeInfoInquirer::GetInstance().ListCurrentInputMethodSubtype(currentUserId, subProps);
604     EXPECT_EQ(ret, ErrorCode::ERROR_BAD_PARAMETERS);
605 }
606 
607 /**
608  * @tc.name: III_TestListInputMethod_001
609  * @tc.desc: status is error
610  * @tc.type: FUNC
611  * @tc.require:
612  * @tc.author: chenyu
613  */
614 HWTEST_F(InputMethodPrivateMemberTest, III_TestListInputMethod_001, TestSize.Level0)
615 {
616     IMSA_HILOGI("InputMethodPrivateMemberTest III_TestListInputMethod_001 TEST START");
617     std::vector<Property> props;
618     auto ret = ImeInfoInquirer::GetInstance().ListInputMethod(60, InputMethodStatus(10), props, false);
619     EXPECT_EQ(ret, ErrorCode::ERROR_BAD_PARAMETERS);
620 }
621 
622 /**
623  * @tc.name: III_TestIsNewExtInfos_001
624  * @tc.desc: has no metadata name = SUBTYPE_PROFILE_METADATA_NAME
625  * @tc.type: FUNC
626  * @tc.require:
627  * @tc.author: chenyu
628  */
629 HWTEST_F(InputMethodPrivateMemberTest, III_TestIsNewExtInfos_001, TestSize.Level0)
630 {
631     IMSA_HILOGI("InputMethodPrivateMemberTest III_TestIsNewExtInfos_001 TEST START");
632     ExtensionAbilityInfo extInfo;
633     std::vector<SubProperty> subProps;
634     auto ret = ImeInfoInquirer::GetInstance().ListInputMethodSubtype(50, extInfo, subProps);
635     EXPECT_EQ(ret, ErrorCode::ERROR_BAD_PARAMETERS);
636 }
637 
638 /**
639  * @tc.name: ICM_TestDeleteImeCfg_001
640  * @tc.desc: delete ime cfg correctly
641  * @tc.type: FUNC
642  * @tc.require:
643  * @tc.author: chenyu
644  */
645 HWTEST_F(InputMethodPrivateMemberTest, ICM_TestDeleteImeCfg_001, TestSize.Level0)
646 {
647     IMSA_HILOGI("InputMethodPrivateMemberTest ICM_TestDeleteImeCfg_001 TEST START");
648     ImeCfgManager::GetInstance().imeConfigs_.push_back({ 100, "testBundleName", "testSubName", false});
649     ImeCfgManager::GetInstance().DeleteImeCfg(100);
650     EXPECT_TRUE(ImeCfgManager::GetInstance().imeConfigs_.empty());
651 }
652 
653 /**
654  * @tc.name: WMSConnectObserver_001
655  * @tc.desc:
656  * @tc.type: FUNC
657  * @tc.require:
658  * @tc.author: chenyu
659  */
660 HWTEST_F(InputMethodPrivateMemberTest, WMSConnectObserver_001, TestSize.Level0)
661 {
662     IMSA_HILOGI("InputMethodPrivateMemberTest WMSConnectObserver_001 TEST START");
663     WmsConnectionObserver observer(nullptr);
664     WmsConnectionObserver::connectedUserId_.clear();
665     int32_t userId = 100;
666     int32_t screenId = 0;
667 
668     observer.OnConnected(userId, screenId);
669     EXPECT_EQ(WmsConnectionObserver::connectedUserId_.size(), 1);
670     EXPECT_TRUE(WmsConnectionObserver::IsWmsConnected(userId));
671 
672     int32_t userId1 = 102;
673     observer.OnConnected(userId1, screenId);
674     EXPECT_EQ(WmsConnectionObserver::connectedUserId_.size(), 2);
675     EXPECT_TRUE(WmsConnectionObserver::IsWmsConnected(userId1));
676 
677     observer.OnConnected(userId, screenId);
678     EXPECT_EQ(WmsConnectionObserver::connectedUserId_.size(), 2);
679 
680     observer.OnDisconnected(userId, screenId);
681     EXPECT_EQ(WmsConnectionObserver::connectedUserId_.size(), 1);
682     EXPECT_FALSE(WmsConnectionObserver::IsWmsConnected(userId));
683 }
684 
685 /**
686  * @tc.name: IMC_testDeactivateClient
687  * @tc.desc: DeactivateClient
688  * @tc.type: FUNC
689  * @tc.require:
690  * @tc.author: chenyu
691  */
692 HWTEST_F(InputMethodPrivateMemberTest, IMC_testDeactivateClient, TestSize.Level0)
693 {
694     IMSA_HILOGI("InputMethodPrivateMemberTest IMC_testDeactivateClient Test START");
695     auto imc = InputMethodController::GetInstance();
696     imc->agent_ = std::make_shared<InputMethodAgentStub>();
697     MessageParcel data;
698     data.WriteRemoteObject(imc->agent_->AsObject());
699     imc->agentObject_ = data.ReadRemoteObject();
700     imc->clientInfo_.state = ClientState::ACTIVE;
701     imc->DeactivateClient();
702     EXPECT_EQ(imc->clientInfo_.state, ClientState::INACTIVE);
703     EXPECT_NE(imc->agent_, nullptr);
704     EXPECT_NE(imc->agentObject_, nullptr);
705 }
706 
707 /**
708  * @tc.name: testIsPanelShown
709  * @tc.desc: Test Panel Shown.
710  * @tc.type: FUNC
711  */
712 HWTEST_F(InputMethodPrivateMemberTest, testIsPanelShown, TestSize.Level0)
713 {
714     IMSA_HILOGI("InputMethodPrivateMemberTest testIsPanelShown TEST START");
715     auto userSession = std::make_shared<PerUserSession>(MAIN_USER_ID);
716     PanelInfo panelInfo = { .panelType = SOFT_KEYBOARD, .panelFlag = FLG_FIXED };
717     bool flag = true;
718     auto ret = userSession->IsPanelShown(panelInfo, flag);
719     EXPECT_EQ(ret, ErrorCode::NO_ERROR);
720 }
721 
722 /**
723  * @tc.name: TestGetDefaultInputMethod_001
724  * @tc.desc: TestGetDefaultInputMethod
725  * @tc.type: FUNC
726  * @tc.require:
727  */
728 HWTEST_F(InputMethodPrivateMemberTest, TestGetDefaultInputMethod_001, TestSize.Level0)
729 {
730     IMSA_HILOGI("InputMethodPrivateMemberTest TestGetDefaultInputMethod_001 TEST START");
731     // currentIme is empty
732     std::shared_ptr<Property> prop;
733     auto currentUserId = TddUtil::GetCurrentUserId();
734     auto ret = ImeInfoInquirer::GetInstance().GetDefaultInputMethod(currentUserId, prop, false);
735     EXPECT_EQ(ret, ErrorCode::NO_ERROR);
736 }
737 
738 /**
739  * @tc.name: TestGetDefaultInputMethod_002
740  * @tc.desc: TestGetDefaultInputMethod
741  * @tc.type: FUNC
742  * @tc.require:
743  */
744 HWTEST_F(InputMethodPrivateMemberTest, TestGetDefaultInputMethod_002, TestSize.Level0)
745 {
746     IMSA_HILOGI("InputMethodPrivateMemberTest TestGetDefaultInputMethod_002 TEST START");
747     // currentIme is empty
748     std::shared_ptr<Property> prop;
749     auto currentUserId = TddUtil::GetCurrentUserId();
750     auto ret = ImeInfoInquirer::GetInstance().GetDefaultInputMethod(currentUserId, prop, true);
751     EXPECT_EQ(ret, ErrorCode::NO_ERROR);
752 }
753 
754 /**
755  * @tc.name: TestGetResMgr
756  * @tc.desc: GetResMgr
757  * @tc.type: FUNC
758  * @tc.require:
759  */
760 HWTEST_F(InputMethodPrivateMemberTest, TestGetResMgr, TestSize.Level0)
761 {
762     IMSA_HILOGI("InputMethodPrivateMemberTest TestGetResMgr TEST START");
763     // currentIme is empty
764     auto ret = ImeInfoInquirer::GetInstance().GetResMgr("/test");
765     EXPECT_TRUE(ret != nullptr);
766 }
767 
768 /**
769  * @tc.name: TestQueryFullImeInfo
770  * @tc.desc: QueryFullImeInfo
771  * @tc.type: FUNC
772  * @tc.require:
773  */
774 HWTEST_F(InputMethodPrivateMemberTest, TestQueryFullImeInfo, TestSize.Level0)
775 {
776     IMSA_HILOGI("InputMethodPrivateMemberTest TestQueryFullImeInfo TEST START");
777     auto currentUserId = TddUtil::GetCurrentUserId();
778     std::vector<FullImeInfo> infos;
779     auto ret = ImeInfoInquirer::GetInstance().QueryFullImeInfo(currentUserId, infos);
780     EXPECT_EQ(ret, ErrorCode::NO_ERROR);
781 }
782 
783 /**
784  * @tc.name: TestIsInputMethod
785  * @tc.desc: IsInputMethod
786  * @tc.type: FUNC
787  * @tc.require:
788  */
789 HWTEST_F(InputMethodPrivateMemberTest, TestIsInputMethod, TestSize.Level0)
790 {
791     IMSA_HILOGI("InputMethodPrivateMemberTest TestIsInputMethod TEST START");
792     auto currentUserId = TddUtil::GetCurrentUserId();
793     auto bundleName = "testBundleName1";
794     auto ret = ImeInfoInquirer::GetInstance().IsInputMethod(currentUserId, bundleName);
795     EXPECT_EQ(ret, ErrorCode::NO_ERROR);
796 }
797 
798  /**
799  @tc.name: TestHandlePackageEvent
800  @tc.desc: TestHandlePackageEvent
801  @tc.type: FUNC
802  @tc.require:
803  */
804 HWTEST_F(InputMethodPrivateMemberTest, TestHandlePackageEvent, TestSize.Level0)
805 {
806 // msg is nullptr
807     auto *msg = new Message(MessageID::MSG_ID_PACKAGE_REMOVED, nullptr);
808     auto ret = service_->HandlePackageEvent(msg);
809     EXPECT_EQ(ret, ErrorCode::ERROR_NULL_POINTER);
810     MessageHandler::Instance()->SendMessage(msg);
811 
812     // PARCELABLE failed
813     MessageParcel *parcel1 = new (std::nothrow) MessageParcel();
814     auto bundleName = "testBundleName1";
815     parcel1->WriteString(bundleName);
816     auto msg1 = std::make_shared<Message>(MessageID::MSG_ID_PACKAGE_REMOVED, parcel1);
817     auto ret1 = service_->HandlePackageEvent(msg1.get());
818     EXPECT_EQ(ret1, ErrorCode::ERROR_EX_PARCELABLE);
819 
820     // userId is not same
821     auto parcel2 = new (std::nothrow) MessageParcel();
822     auto userId = 50;
823     service_->userId_ = 60;
824     parcel2->WriteInt32(userId);
825     parcel2->WriteString(bundleName);
826     auto msg2 = std::make_shared<Message>(MessageID::MSG_ID_PACKAGE_REMOVED, parcel2);
827     auto ret2 = service_->HandlePackageEvent(msg2.get());
828     EXPECT_EQ(ret2, ErrorCode::NO_ERROR);
829 
830     //remove bundle not current ime
831     auto parcel3 = new (std::nothrow) MessageParcel();
832     service_->userId_ = userId;
833     ImeCfgManager::GetInstance().imeConfigs_.push_back({ 60, "testBundleName/testExtName", "testSubName", false });
834     parcel3->WriteInt32(userId);
835     parcel3->WriteString(bundleName);
836     auto msg3 = std::make_shared<Message>(MessageID::MSG_ID_PACKAGE_REMOVED, parcel3);
837     auto ret3 = service_->HandlePackageEvent(msg3.get());
838     EXPECT_EQ(ret3, ErrorCode::NO_ERROR);
839 }
840 } // namespace MiscServices
841 } // namespace OHOS