• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2023-2024 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "call_voice_assistant_manager.h"
17 #include "distributed_call_manager.h"
18 
19 namespace {
20     ffrt::queue callVoiceAssistantQueue { "call_voice_assistant_manager" };
21 }
22 
23 namespace OHOS {
24 namespace Telephony {
25 
26 std::shared_ptr<VoiceAssistantRingSubscriber> VoiceAssistantRingSubscriber::subscriber_ = nullptr;
27 std::shared_ptr<CallVoiceAssistantManager> CallVoiceAssistantManager::mInstance_ =
28     std::make_shared<CallVoiceAssistantManager>();
29 
GetInstance()30 std::shared_ptr<CallVoiceAssistantManager> CallVoiceAssistantManager::GetInstance()
31 {
32     if (mInstance_ != nullptr) {
33         return mInstance_;
34     }
35     return std::make_shared<CallVoiceAssistantManager>();
36 };
37 
IsStartVoiceBroadcast()38 bool CallVoiceAssistantManager::IsStartVoiceBroadcast()
39 {
40     if (!isQueryedBroadcastSwitch) {
41         TELEPHONY_LOGI("first query broad switch");
42         bool queryResult = IsSwitchOn(BROADCAST_SWITCH);
43         isBroadcastSwitchOn = queryResult;
44         isQueryedBroadcastSwitch = true;
45         return queryResult;
46     }
47     return isBroadcastSwitchOn;
48 }
49 
Initial()50 std::shared_ptr<DataShare::DataShareHelper> CallVoiceAssistantManager::Initial()
51 {
52     sptr<ISystemAbilityManager> saManager = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
53     if (saManager == nullptr) {
54         TELEPHONY_LOGE("saManager is nullptr");
55         return nullptr;
56     }
57     sptr<IRemoteObject> remote = saManager->GetSystemAbility(OHOS::TELEPHONY_CALL_MANAGER_SYS_ABILITY_ID);
58     if (remote == nullptr) {
59         TELEPHONY_LOGE("remote is nullptr");
60         return nullptr;
61     }
62     return DataShare::DataShareHelper::Creator(remote, SETTINGS_DATASHARE_URI, SETTINGS_DATASHARE_EXT_URI);
63 };
64 
~CallVoiceAssistantManager()65 CallVoiceAssistantManager::~CallVoiceAssistantManager()
66 {
67     OnStopService();
68 }
69 
Release()70 void CallVoiceAssistantManager::Release()
71 {
72     connectCallback_ = nullptr;
73     settingsCallback_ = nullptr;
74     mRemoteObject = nullptr;
75     isBroadcastSwitchOn = false;
76     isControlSwitchOn = false;
77     isQueryedBroadcastSwitch = false;
78     isConnectService = false;
79     broadcastCheck = DEFAULT_STRING;
80     isplay = SWITCH_TURN_OFF;
81 };
82 
IsSwitchOn(const std::string & switchState)83 bool CallVoiceAssistantManager::IsSwitchOn(const std::string& switchState)
84 {
85     bool isHiCarConnected = DelayedSingleton<DistributedCallManager>::GetInstance()->IsDistributedCarDeviceOnline();
86     if (isHiCarConnected) {
87         TELEPHONY_LOGI("hicar is connected, voice control by hicar");
88         return true;
89     }
90     int32_t userId = 0;
91     bool isUserUnlocked = false;
92     AccountSA::OsAccountManager::GetForegroundOsAccountLocalId(userId);
93     AccountSA::OsAccountManager::IsOsAccountVerified(userId, isUserUnlocked);
94     if (!isUserUnlocked) {
95         TELEPHONY_LOGE("user is locked");
96         return false;
97     }
98     std::string value = SWITCH_TURN_OFF;
99     this->QueryValue(switchState, value);
100     TELEPHONY_LOGI("%{public}s is %{public}s", switchState.c_str(), value.c_str());
101     if (value == SWITCH_TURN_OFF) {
102         return false;
103     }
104     return true;
105 };
106 
RegisterListenSwitchState()107 bool CallVoiceAssistantManager::RegisterListenSwitchState()
108 {
109     if (settingsCallback_ == nullptr) {
110         settingsCallback_ = sptr<VoiceAssistantSwitchObserver>::MakeSptr();
111         if (settingsCallback_ == nullptr) {
112             TELEPHONY_LOGE("settingsCallback is nullptr");
113             return false;
114         }
115         auto datashareHelper_ = Initial();
116         if (datashareHelper_ == nullptr) {
117             TELEPHONY_LOGE("datashareHelper is nullptr");
118             return false;
119         }
120         OHOS::Uri uri_listen(SETTINGS_DATASHARE_URI_KEY + CONTROL_SWITCH);
121         datashareHelper_->RegisterObserver(uri_listen, settingsCallback_);
122         datashareHelper_->Release();
123     }
124     TELEPHONY_LOGI("listen success");
125     return true;
126 };
127 
UnRegisterListenSwitchState()128 bool CallVoiceAssistantManager::UnRegisterListenSwitchState()
129 {
130     if (settingsCallback_ == nullptr) {
131         TELEPHONY_LOGE("listen already close");
132         return false;
133     };
134     auto datashareHelper_ = Initial();
135     if (datashareHelper_ == nullptr) {
136         TELEPHONY_LOGE("datashareHelper is nullptr");
137         return false;
138     }
139     OHOS::Uri uri_listen(SETTINGS_DATASHARE_URI_KEY + CONTROL_SWITCH);
140     datashareHelper_->UnregisterObserver(uri_listen, settingsCallback_);
141     datashareHelper_->Release();
142     TELEPHONY_LOGI("listen close success");
143     return true;
144 };
145 
ConnectAbility(int32_t callId)146 bool CallVoiceAssistantManager::ConnectAbility(int32_t callId)
147 {
148     if (connectCallback_ == nullptr) {
149         connectCallback_ = sptr<VoiceAssistantConnectCallback>::MakeSptr(callId);
150         if (connectCallback_ == nullptr) {
151             TELEPHONY_LOGE("connectCallback is nullptr");
152             return false;
153         }
154     }
155     bool isHiCarConnected = DelayedSingleton<DistributedCallManager>::GetInstance()->IsDistributedCarDeviceOnline();
156     AAFwk::Want want;
157     AppExecFwk::ElementName element(
158         DEFAULT_STRING, isHiCarConnected ? HICAR_BUNDLE_NAME : BUNDLE_NAME, ABILITY_NAME);
159     want.SetElement(element);
160     int32_t userId = FAIL_CODE;
161     auto ret = AAFwk::AbilityManagerClient::GetInstance()->ConnectAbility(want, connectCallback_, userId);
162     if (ret != TELEPHONY_SUCCESS && isBroadcastSwitchOn) {
163         VoiceAssistantRingSubscriber::Initial();
164         isplay = SWITCH_TURN_ON;
165         isConnectService = false;
166         PublishCommonEvent(false, std::string("connect_voice_assistant_ability_failed"));
167     }
168     return ret == TELEPHONY_SUCCESS;
169 };
170 
DisconnectAbility()171 bool CallVoiceAssistantManager::DisconnectAbility()
172 {
173     if (connectCallback_ == nullptr) {
174         TELEPHONY_LOGI("disconnectAbility already close");
175         return false;
176     }
177     auto ret = AAFwk::AbilityManagerClient::GetInstance()->DisconnectAbility(connectCallback_);
178     TELEPHONY_LOGI("disconnectAbility %{public}d", ret);
179     return true;
180 };
181 
PublishCommonEvent(bool isConnect,std::string publisher)182 void CallVoiceAssistantManager::PublishCommonEvent(bool isConnect, std::string publisher)
183 {
184     if (connectCallback_ == nullptr) {
185         TELEPHONY_LOGI("service is not start");
186         return;
187     }
188     if (isConnect) {
189         isConnect = isConnectService;
190     }
191     std::string startService = isConnect ? SWITCH_TURN_ON : SWITCH_TURN_OFF;
192     EventFwk::Want want;
193     want.SetAction(CONTROL_SWITCH_STATE_CHANGE_EVENT);
194     want.SetParam(IS_CONNECT_SERVICE, startService);
195     want.SetParam(CONTROL_SWITCH.c_str(), controlCheck);
196     want.SetParam(BROADCAST_SWITCH.c_str(), broadcastCheck);
197     want.SetParam(IS_PLAY_RING, isplay);
198     want.SetParam("publisher_name", publisher);
199     EventFwk::CommonEventData data;
200     data.SetWant(want);
201     EventFwk::CommonEventPublishInfo publishInfo;
202     std::vector<std::string> recePermissions;
203     recePermissions.emplace_back("ohos.permission.ANSWER_CALL");
204     publishInfo.SetSubscriberPermissions(recePermissions);
205     EventFwk::CommonEventManager::PublishCommonEvent(data, publishInfo, nullptr);
206     TELEPHONY_LOGI("publish commonEvent done, [%{public}s].", publisher.c_str());
207 }
208 
OnStartService(const std::string & isDial,const int32_t & callId)209 void CallVoiceAssistantManager::OnStartService(const std::string& isDial, const int32_t& callId)
210 {
211     if (mRemoteObject != nullptr) {
212         TELEPHONY_LOGI("mRemote Object is not nullptr");
213         this->SendRequest(accountIds[callId], true);
214         return;
215     }
216     OnStopService();
217     if (isDial == INCOMING) {
218         IsStartVoiceBroadcast();
219     }
220     isControlSwitchOn = IsSwitchOn(CONTROL_SWITCH);
221     if (!isControlSwitchOn && !isBroadcastSwitchOn) {
222         TELEPHONY_LOGE("the switch is all close");
223         return;
224     }
225     if (ConnectAbility(callId)) {
226         TELEPHONY_LOGI("start service success");
227         return;
228     }
229     TELEPHONY_LOGE("start service failed");
230 };
231 
OnStopService()232 void CallVoiceAssistantManager::OnStopService()
233 {
234     DisconnectAbility();
235     UnRegisterListenSwitchState();
236     VoiceAssistantRingSubscriber::Release();
237     PublishCommonEvent(false, std::string("on_stop_service"));
238     Release();
239 };
240 
QueryValue(const std::string & key,std::string & value)241 int CallVoiceAssistantManager::QueryValue(const std::string& key, std::string& value)
242 {
243     auto datashareHelper_ = Initial();
244     if (datashareHelper_ == nullptr) {
245         TELEPHONY_LOGE("datashareHelper is nullptr");
246         return FAIL_CODE;
247     }
248     std::vector<std::string> columns;
249     DataShare::DataSharePredicates predicates;
250     predicates.EqualTo("KEYWORD", key);
251     OHOS::Uri uri(SETTINGS_DATASHARE_URI_KEY + key);
252     auto result = datashareHelper_->Query(uri, predicates, columns);
253     datashareHelper_->Release();
254     if (result == nullptr) {
255         TELEPHONY_LOGE("result is nullptr");
256         return FAIL_CODE;
257     }
258     int rowCount = 0;
259     result->GetRowCount(rowCount);
260     if (rowCount == 0) {
261         TELEPHONY_LOGI("rowCount is 0");
262         result->Close();
263         return FAIL_CODE;
264     }
265     if (result->GoToFirstRow() != DataShare::E_OK) {
266         TELEPHONY_LOGE("gotofirst row error");
267         result->Close();
268         return FAIL_CODE;
269     }
270     int columnIndex = 0;
271     result->GetColumnIndex("VALUE", columnIndex);
272     result->GetString(columnIndex, value);
273     result->Close();
274     return TELEPHONY_SUCCESS;
275 }
276 
UpdateNumberLocation(const std::string & location,int32_t callId)277 void CallVoiceAssistantManager::UpdateNumberLocation(const std::string& location, int32_t callId)
278 {
279     callVoiceAssistantQueue.submit([=]() {
280         TELEPHONY_LOGI("update location callId, %{public}d", callId);
281         auto it_callId = accountIds.find(callId);
282         if (it_callId == accountIds.end()) {
283             TELEPHONY_LOGE("iterator is end");
284             return;
285         }
286         auto nowInfo = it_callId->second;
287         if (nowInfo == nullptr) {
288             TELEPHONY_LOGE("info is nullptr");
289             return;
290         }
291         if ((TelCallState)nowInfo->call_status == TelCallState::CALL_STATUS_DIALING) {
292             TELEPHONY_LOGE("dialing without number location");
293             return;
294         }
295         nowInfo->numberLocation = location;
296         SendRequest(nowInfo, true);
297     });
298 }
299 
GetContactInfo(int32_t callId)300 std::shared_ptr<IncomingContactInformation> CallVoiceAssistantManager::GetContactInfo(int32_t callId)
301 {
302     if (accountIds[callId] == nullptr) {
303         TELEPHONY_LOGI("initial accountIds callId, %{public}d", callId);
304         accountIds[callId] = std::make_shared<IncomingContactInformation>();
305     }
306     return accountIds[callId];
307 }
308 
UpdateRemoteObject(const sptr<IRemoteObject> & object,int32_t callId,const sptr<AAFwk::IAbilityConnection> callback)309 void CallVoiceAssistantManager::UpdateRemoteObject(const sptr<IRemoteObject> &object, int32_t callId,
310     const sptr<AAFwk::IAbilityConnection> callback)
311 {
312     callVoiceAssistantQueue.submit([=]() {
313         TELEPHONY_LOGI("update remote object callId, %{public}d", callId);
314         if (nowCallId != callId || accountIds.find(callId) == accountIds.end()) {
315             TELEPHONY_LOGE("nowCallId, %{public}d", nowCallId);
316             AAFwk::AbilityManagerClient::GetInstance()->DisconnectAbility(callback);
317             return;
318         }
319         mRemoteObject = object;
320         this->SendRequest(accountIds[callId], true);
321     });
322 }
323 
UpdateContactInfo(const ContactInfo & info,int32_t callId)324 void CallVoiceAssistantManager::UpdateContactInfo(const ContactInfo& info, int32_t callId)
325 {
326     callVoiceAssistantQueue.submit([=]() {
327         TELEPHONY_LOGI("update contact info callId, %{public}d", callId);
328         auto it_callId = accountIds.find(callId);
329         if (it_callId == accountIds.end()) {
330             TELEPHONY_LOGE("iterator is end");
331             return;
332         }
333         auto nowInfo = it_callId->second;
334         if (nowInfo == nullptr) {
335             TELEPHONY_LOGE("info is nullptr");
336             return;
337         }
338         if ((TelCallState)nowInfo->call_status == TelCallState::CALL_STATUS_DIALING) {
339             TELEPHONY_LOGE("dialing without contact info");
340             return;
341         }
342         nowInfo->incomingName = info.name;
343         nowInfo->phoneNumber = info.number;
344         nowInfo->isQueryComplete = info.isQueryComplete;
345         nowInfo->isContact = (nowInfo->incomingName == "") ? SWITCH_TURN_OFF : SWITCH_TURN_ON;
346         SendRequest(nowInfo, true);
347     });
348 }
349 
MuteRinger()350 void CallVoiceAssistantManager::MuteRinger()
351 {
352     callVoiceAssistantQueue.submit([=]() {
353         TELEPHONY_LOGI("stop broadcast event");
354         VoiceAssistantRingSubscriber::Release();
355         isplay = SWITCH_TURN_OFF;
356         if (nowCallId == FAIL_CODE) {
357             TELEPHONY_LOGE("nowCallId is invalid");
358             return;
359         }
360         auto info = accountIds[nowCallId];
361         if (info != nullptr) {
362             info->stopBroadcasting = 1;
363         }
364         this->SendRequest(info, false);
365         this->PublishCommonEvent(isConnectService, std::string("stop_broadcast_event"));
366     });
367 }
368 
SendRequest(const std::shared_ptr<IncomingContactInformation> info,bool isNeed)369 void CallVoiceAssistantManager::SendRequest(const std::shared_ptr<IncomingContactInformation> info, bool isNeed)
370 {
371     if (mRemoteObject == nullptr) {
372         TELEPHONY_LOGE("mRemoteObject is nullptr");
373         return;
374     }
375     if (info == nullptr) {
376         TELEPHONY_LOGE("info is nullptr");
377         return;
378     }
379     if (!info->isQueryComplete || info->dialOrCome == DEFAULT_STRING || info->numberLocation == "default") {
380         TELEPHONY_LOGE("exist null string: %{public}s.", (info->dialOrCome).c_str());
381         return;
382     }
383     MessageParcel data;
384     MessageParcel reply;
385     MessageOption option;
386     std::u16string sendStr = GetSendString(info);
387     if (sendStr == DEFAULT_U16STRING) {
388         TELEPHONY_LOGE("send string is invalid");
389         return;
390     }
391     data.WriteString16(sendStr);
392     int32_t retCode = mRemoteObject->SendRequest(CHECK_CODE, data, reply, option);
393     TELEPHONY_LOGI("send request ret code: %{public}d.", retCode);
394     if (!isNeed) {
395         return;
396     }
397     isConnectService = false;
398     isplay = SWITCH_TURN_OFF;
399     UpdateReplyData(Str16ToStr8(reply.ReadString16()));
400     if (controlCheck == SWITCH_TURN_ON && isControlSwitchOn) {
401         isConnectService = true;
402         RegisterListenSwitchState();
403     }
404     bool isShouldRing = (broadcastCheck == SWITCH_TURN_ON || retCode != TELEPHONY_SUCCESS);
405     if (isShouldRing && isBroadcastSwitchOn && info->stopBroadcasting == 0 && info->dialOrCome != DIALING) {
406         VoiceAssistantRingSubscriber::Initial();
407         isplay = SWITCH_TURN_ON;
408     }
409     PublishCommonEvent(isConnectService, std::string("remote_object_send_request"));
410 }
411 
OnAbilityConnectDone(const AppExecFwk::ElementName & element,const sptr<IRemoteObject> & remoteObject,int resultCode)412 void VoiceAssistantConnectCallback::OnAbilityConnectDone(const AppExecFwk::ElementName &element,
413     const sptr<IRemoteObject> &remoteObject, int resultCode)
414 {
415     TELEPHONY_LOGI("connect callback result code, %{public}d", resultCode);
416     if (remoteObject == nullptr) {
417         TELEPHONY_LOGE("RemoteObject is nullptr");
418         return;
419     }
420     if (resultCode == TELEPHONY_SUCCESS) {
421         sptr<AAFwk::IAbilityConnection> callback = sptr<AAFwk::IAbilityConnection>(this);
422         CallVoiceAssistantManager::GetInstance()->UpdateRemoteObject(remoteObject, startId, callback);
423     }
424 };
425 
OnAbilityDisconnectDone(const AppExecFwk::ElementName & element,int resultCode)426 void VoiceAssistantConnectCallback::OnAbilityDisconnectDone(const AppExecFwk::ElementName &element, int resultCode)
427 {
428     TELEPHONY_LOGI("disconnect callback result code, %{public}d", resultCode);
429 };
430 
GetSendString(const std::shared_ptr<IncomingContactInformation> nowInfo)431 std::u16string CallVoiceAssistantManager::GetSendString(const std::shared_ptr<IncomingContactInformation> nowInfo)
432 {
433     if (nowInfo == nullptr) {
434         TELEPHONY_LOGE("nowInfo is nullptr");
435         return DEFAULT_U16STRING;
436     }
437     if (Str8ToStr16(nowInfo->incomingName) == DEFAULT_U16STRING) {
438         TELEPHONY_LOGE("incomingName is invalid.");
439         nowInfo->incomingName = DEFAULT_STRING;
440     }
441     if (Str8ToStr16(nowInfo->numberLocation) == DEFAULT_U16STRING) {
442         TELEPHONY_LOGE("numberLocation is invalid.");
443         nowInfo->numberLocation = DEFAULT_STRING;
444     }
445     if (Str8ToStr16(nowInfo->phoneNumber) == DEFAULT_U16STRING) {
446         TELEPHONY_LOGE("phoneNumber is invalid.");
447         nowInfo->phoneNumber = DEFAULT_STRING;
448     }
449     std::string str = DEFAULT_STRING;
450     auto fun = [&str](std::string key, std::string value, bool start = false, bool end = false) {
451         std::string first = (start) ? "{" : "";
452         std::string last = (end) ? "}" : ",";
453         str = str + first + "\"" + key + "\"" + ":" + "\"" + value + "\"" + last;
454     };
455     fun("dialOrCome", nowInfo->dialOrCome, true);
456     fun("callStatus", std::to_string(nowInfo->call_status));
457     fun("callId", std::to_string(nowInfo->callId));
458     fun("phoneNumber", nowInfo->phoneNumber);
459     fun("isContact", nowInfo->isContact);
460     fun("contactName", nowInfo->incomingName);
461     fun("sim", std::to_string(nowInfo->accountId));
462     fun("stopBroadcasting", std::to_string(nowInfo->stopBroadcasting));
463     fun("location", nowInfo->numberLocation, false, true);
464     return Str8ToStr16(str);
465 }
466 
OnChange()467 void VoiceAssistantSwitchObserver::OnChange()
468 {
469     auto voicePtr = CallVoiceAssistantManager::GetInstance();
470     if (voicePtr == nullptr) {
471         TELEPHONY_LOGE("voicePtr is nullptr");
472         return;
473     }
474     std::string switch_off = voicePtr->SWITCH_TURN_OFF;
475     auto lastControlVal = voicePtr->GetIsControlSwitchOn();
476     if (!lastControlVal) {
477         TELEPHONY_LOGI("the controlswitch already close");
478         return;
479     }
480     auto ret = voicePtr->IsSwitchOn(voicePtr->CONTROL_SWITCH);
481     if (lastControlVal && !ret) {
482         TELEPHONY_LOGI("controlswitch from true to false");
483         voicePtr->PublishCommonEvent(false, std::string("control_switch_state_on_change"));
484         voicePtr->SetIsControlSwitchOn(false);
485     }
486 }
487 
CallStateUpdated(sptr<CallBase> & callObjectPtr,TelCallState priorState,TelCallState nextState)488 void CallVoiceAssistantManager::CallStateUpdated(
489     sptr<CallBase> &callObjectPtr, TelCallState priorState, TelCallState nextState)
490 {
491     callVoiceAssistantQueue.submit([=]() {
492         if (callObjectPtr == nullptr) {
493             TELEPHONY_LOGE("callobject is nullptr");
494             return;
495         }
496         TelCallState callState = callObjectPtr->GetTelCallState();
497         if (callState != TelCallState::CALL_STATUS_ACTIVE && callState != TelCallState::CALL_STATUS_DIALING &&
498             callState != TelCallState::CALL_STATUS_INCOMING && callState != TelCallState::CALL_STATUS_DISCONNECTED) {
499             return;
500         }
501         int32_t callId = callObjectPtr->GetCallID();
502         int32_t accountId = callObjectPtr->GetAccountId();
503         auto info = GetContactInfo(callId);
504         if (info != nullptr) {
505             info->call_status = (int32_t)callState;
506             info->accountId = accountId;
507             info->callId = callId;
508             info->call = callObjectPtr;
509         }
510         switch (callState) {
511             case TelCallState::CALL_STATUS_ACTIVE:
512                 CallStatusActive(callId, accountId);
513                 break;
514             case TelCallState::CALL_STATUS_DIALING:
515                 CallStatusDialing(callId, accountId);
516                 break;
517             case TelCallState::CALL_STATUS_INCOMING:
518                 if (!CallObjectManager::IsNeedSilentInDoNotDisturbMode()) {
519                     CallStatusIncoming(callId, accountId);
520                 } else {
521                     TELEPHONY_LOGI("need silent, no need voice assistant");
522                 }
523                 break;
524             case TelCallState::CALL_STATUS_DISCONNECTED:
525                 CallStatusDisconnected(callId, accountId);
526                 break;
527             default:
528                 break;
529         }
530     });
531 }
532 
UpdateVoipCallState(int32_t state)533 void CallVoiceAssistantManager::UpdateVoipCallState(int32_t state)
534 {
535     TELEPHONY_LOGI("voip callstate is %{public}d", state);
536     nowVoipCallState = state;
537 }
538 
CallStatusIncoming(const int32_t & callId,const int32_t & accountId)539 void CallVoiceAssistantManager::CallStatusIncoming(const int32_t& callId, const int32_t& accountId)
540 {
541     if (nowCallId != callId && nowAccountId != accountId) {
542         TELEPHONY_LOGI("call_status_incoming, [%{public}d][%{public}d]", accountId, callId);
543         if ((CallStateToApp)nowVoipCallState == CallStateToApp::CALL_STATE_OFFHOOK) {
544             TELEPHONY_LOGE("the meetime callstate is off_hook");
545             OnStopService();
546             return;
547         }
548         auto info = accountIds[callId];
549         if (info == nullptr) {
550             TELEPHONY_LOGE("info is nullptr");
551             return;
552         }
553         info->dialOrCome = INCOMING;
554         if (CheckTelCallState(TelCallState::CALL_STATUS_ACTIVE) != FAIL_CODE) {
555             return;
556         }
557         if (CheckTelCallState(TelCallState::CALL_STATUS_DIALING) != FAIL_CODE) {
558             info->dialOrCome = DIALING;
559         }
560         if (info->call != nullptr) {
561             ContactInfo contactInfo = info->call->GetCallerInfo();
562             info->numberLocation = info->call->GetNumberLocation();
563             info->incomingName = contactInfo.name;
564             info->phoneNumber = contactInfo.number;
565             info->isContact = (info->incomingName == "") ? SWITCH_TURN_OFF : SWITCH_TURN_ON;
566             info->isQueryComplete = contactInfo.isQueryComplete;
567         }
568         nowCallId = callId;
569         nowAccountId = accountId;
570         OnStartService(info->dialOrCome, callId);
571     }
572 }
573 
CallStatusDialing(const int32_t & callId,const int32_t & accountId)574 void CallVoiceAssistantManager::CallStatusDialing(const int32_t& callId, const int32_t& accountId)
575 {
576     auto info = accountIds[callId];
577     if (info == nullptr) {
578         TELEPHONY_LOGE("info is nullptr");
579         return;
580     }
581     if (nowCallId != callId && nowAccountId != accountId) {
582         TELEPHONY_LOGI("call_status_dialing, [%{public}d][%{public}d]", accountId, callId);
583         info->dialOrCome = DIALING;
584         info->numberLocation = DIALING;
585         info->phoneNumber = DIALING;
586         info->isQueryComplete = true;
587         nowCallId = callId;
588         nowAccountId = accountId;
589         OnStartService(info->dialOrCome, callId);
590     }
591 }
592 
CallStatusActive(const int32_t & callId,const int32_t & accountId)593 void CallVoiceAssistantManager::CallStatusActive(const int32_t& callId, const int32_t& accountId)
594 {
595     TELEPHONY_LOGI("call_status_active, [%{public}d][%{public}d]", accountId, callId);
596     VoiceAssistantRingSubscriber::Release();
597     PublishCommonEvent(false, std::string("call_status_active"));
598     mRemoteObject = nullptr;
599     isQueryedBroadcastSwitch = false;
600 }
601 
CallStatusDisconnected(const int32_t & callId,const int32_t & accountId)602 void CallVoiceAssistantManager::CallStatusDisconnected(const int32_t& callId, const int32_t& accountId)
603 {
604     TELEPHONY_LOGI("call_status_disconnected, [%{public}d][%{public}d]", accountId, callId);
605     auto lastInfo = accountIds[callId];
606     accountIds.erase(callId);
607     if (CheckTelCallState(TelCallState::CALL_STATUS_ACTIVE) != FAIL_CODE) {
608         return;
609     }
610     int32_t comeCallId = CheckTelCallState(TelCallState::CALL_STATUS_INCOMING);
611     TELEPHONY_LOGI("comeCallId, %{public}d.", comeCallId);
612     if (comeCallId != FAIL_CODE) {
613         auto nowInfo = accountIds[comeCallId];
614         if (nowInfo != nullptr && nowInfo->dialOrCome == INCOMING) {
615             nowCallId = nowInfo->callId;
616             nowAccountId = nowInfo->accountId;
617             SendRequest(nowInfo, true);
618         }
619         return;
620     }
621     TELEPHONY_LOGI("accountIds size is %{public}zu", accountIds.size());
622     SendRequest(lastInfo, false);
623     OnStopService();
624     nowCallId = FAIL_CODE;
625     nowAccountId = FAIL_CODE;
626 }
627 
CheckTelCallState(TelCallState state)628 int32_t CallVoiceAssistantManager::CheckTelCallState(TelCallState state)
629 {
630     TELEPHONY_LOGI("check state, %{public}d.", state);
631     int32_t invalid = FAIL_CODE;
632     for (auto& id : accountIds) {
633         if (id.second == nullptr) {
634             TELEPHONY_LOGE("invalid callId, %{public}d.", id.first);
635             invalid = id.first;
636             continue;
637         }
638         TELEPHONY_LOGI("callId %{public}d, state %{public}d.", id.first, id.second->call_status);
639         if ((TelCallState)id.second->call_status == state) {
640             return id.first;
641         }
642     }
643     accountIds.erase(invalid);
644     return FAIL_CODE;
645 }
646 
VoiceAssistantRingSubscriber(const EventFwk::CommonEventSubscribeInfo & subscriberInfo)647 VoiceAssistantRingSubscriber::VoiceAssistantRingSubscriber(const EventFwk::CommonEventSubscribeInfo &subscriberInfo)
648     : EventFwk::CommonEventSubscriber(subscriberInfo) {}
649 
Initial()650 bool VoiceAssistantRingSubscriber::Initial()
651 {
652     if (subscriber_ == nullptr) {
653         auto voicePtr = CallVoiceAssistantManager::GetInstance();
654         if (voicePtr == nullptr) {
655             TELEPHONY_LOGE("voicePtr is nullptr");
656             return false;
657         }
658         EventFwk::MatchingSkills matchingSkills;
659         matchingSkills.AddEvent(voicePtr->CONTROL_SWITCH_STATE_CHANGE_EVENT);
660         EventFwk::CommonEventSubscribeInfo subscribeInfo(matchingSkills);
661         subscribeInfo.SetPermission("ohos.permission.GET_TELEPHONY_STATE");
662         subscriber_ = std::make_shared<VoiceAssistantRingSubscriber>(subscribeInfo);
663         EventFwk::CommonEventManager::SubscribeCommonEvent(subscriber_);
664     }
665     TELEPHONY_LOGI("prepare ring initial");
666     return true;
667 };
668 
Release()669 void VoiceAssistantRingSubscriber::Release()
670 {
671     if (subscriber_ != nullptr) {
672         TELEPHONY_LOGI("stop play system ring");
673         DelayedSingleton<AudioControlManager>::GetInstance()->StopRingtone();
674         EventFwk::CommonEventManager::UnSubscribeCommonEvent(subscriber_);
675         subscriber_ = nullptr;
676     }
677 }
678 
OnReceiveEvent(const EventFwk::CommonEventData & eventData)679 void VoiceAssistantRingSubscriber::OnReceiveEvent(const EventFwk::CommonEventData &eventData)
680 {
681     callVoiceAssistantQueue.submit([=]() {
682         auto voicePtr = CallVoiceAssistantManager::GetInstance();
683         if (voicePtr == nullptr) {
684             TELEPHONY_LOGE("voicePtr is nullptr");
685             return;
686         }
687         const AAFwk::Want &want = eventData.GetWant();
688         std::string action = want.GetAction();
689         if (action != voicePtr->CONTROL_SWITCH_STATE_CHANGE_EVENT) {
690             return;
691         }
692         std::string publisher = want.GetStringParam("publisher_name");
693         if (publisher != std::string("remote_object_send_request") &&
694             publisher != std::string("connect_voice_assistant_ability_failed")) {
695             TELEPHONY_LOGE("publisher name, [%{public}s]", publisher.c_str());
696             return;
697         }
698         std::string isplay = want.GetStringParam(voicePtr->IS_PLAY_RING);
699         bool isPlayRing = voicePtr->GetIsPlayRing();
700         if (isplay == voicePtr->SWITCH_TURN_ON && isPlayRing) {
701             TELEPHONY_LOGI("broadcast switch is open, start play system ring");
702             DelayedSingleton<AudioControlManager>::GetInstance()->StopRingtone();
703             DelayedSingleton<AudioControlManager>::GetInstance()->PlayRingtone();
704         }
705     });
706 };
707 
GetIsPlayRing()708 bool CallVoiceAssistantManager::GetIsPlayRing()
709 {
710     return (isplay == SWITCH_TURN_ON) ? true : false;
711 }
712 
SetIsControlSwitchOn(bool state)713 void CallVoiceAssistantManager::SetIsControlSwitchOn(bool state)
714 {
715     isControlSwitchOn = state;
716 };
717 
GetIsControlSwitchOn()718 bool CallVoiceAssistantManager::GetIsControlSwitchOn()
719 {
720     return isControlSwitchOn;
721 };
722 
UpdateReplyData(const std::string & str)723 void CallVoiceAssistantManager::UpdateReplyData(const std::string& str)
724 {
725     TELEPHONY_LOGI("receiveData, %{public}s.", str.c_str());
726     std::size_t pos1 = 0;
727     std::size_t pos2 = 0;
728     std::map<std::string, std::string> replyData;
729     while (pos1 != std::string::npos && pos2 != std::string::npos) {
730         pos1 = str.find("\"", pos2 + 1);
731         if (pos1 == std::string::npos) {
732             break;
733         }
734         pos2 = str.find("\"", pos1 + 1);
735         if (pos2 == std::string::npos) {
736             break;
737         }
738         auto key = str.substr(pos1 + 1, pos2 -pos1 - 1);
739         pos1 = str.find("\"", pos2 + 1);
740         if (pos1 == std::string::npos) {
741             break;
742         }
743         pos2 = str.find("\"", pos1 + 1);
744         if (pos2 == std::string::npos) {
745             break;
746         }
747         auto value = str.substr(pos1 + 1, pos2 -pos1 - 1);
748         replyData.insert({key, value});
749     }
750     controlCheck = SWITCH_TURN_OFF;
751     broadcastCheck = DEFAULT_STRING;
752     auto it_control = replyData.find(CONTROL_CHECK_RESULT);
753     if (it_control != replyData.end()) {
754         controlCheck = it_control->second;
755     }
756     auto it_broadcast = replyData.find(BROADCAST_CHECK_RESULT);
757     if (it_broadcast != replyData.end()) {
758         broadcastCheck = it_broadcast->second;
759     }
760     TELEPHONY_LOGI("%{public}s, %{public}s.", broadcastCheck.c_str(), controlCheck.c_str());
761 }
762 }
763 }