async def interrupt(self, inner_dc: DialogContext) -> DialogTurnResult: if inner_dc.context.activity.type == ActivityTypes.message: text = inner_dc.context.activity.text.lower() intent, score, luis_result = await LuisHelper.execute_luis_query( self._luis_recognizer, inner_dc.context) if intent == 'help_okr': help_message_text = self._action.get_random_utterance( 'show_help') help_message = MessageFactory.text(help_message_text, help_message_text, InputHints.expecting_input) await inner_dc.context.send_activity(help_message) return DialogTurnResult(DialogTurnStatus.Waiting) elif intent == 'withdraw_okr': cancel_message_text = self._action.get_random_utterance( 'cancel') cancel_message = MessageFactory.text(cancel_message_text, cancel_message_text, InputHints.ignoring_input) await inner_dc.context.send_activity(cancel_message) return await inner_dc.cancel_all_dialogs() return None
async def continue_dialog(self, dialog_context: DialogContext): activity = dialog_context.context.activity if ( activity.type == ActivityTypes.event and activity.name == ActivityEventNames.continue_conversation ): # We continued the conversation, forget the proactive reference. self.continuation_parameters_store[activity.id] = None # The continue conversation activity comes from the ProactiveController when the notification is received await dialog_context.context.send_activity( "We received a proactive message, ending the dialog" ) # End the dialog so the host gets an EoC await dialog_context.context.send_activity( Activity( type=ActivityTypes.end_of_conversation, code=EndOfConversationCodes.completed_successfully, ) ) return DialogTurnResult(DialogTurnStatus.Complete) # Keep waiting for a call to the ProactiveController. await dialog_context.context.send_activity( f"We are waiting for a proactive message. " f"{self.notify_message(self.configuration, activity.from_property.id)}" ) return Dialog.end_of_turn
async def handle_action_step(self, step_context: WaterfallStepContext): action = str(step_context.result.value).lower() if action == "login": return await step_context.begin_dialog( SsoSkillSignInDialog.__name__) if action == "logout": await step_context.context.adapter.sign_out_user( step_context.context, self.connection_name) await step_context.context.send_activity( "You have been signed out.") return await step_context.next(None) if action == "show token": token = await step_context.context.adapter.get_user_token( step_context.context, self.connection_name) if token is None: await step_context.context.send_activity( "User has no cached token.") else: await step_context.context.send_activity( f"Here is your current SSO token: { token.token }") return await step_context.next(None) if action == "end": return DialogTurnResult(DialogTurnStatus.Complete) # This should never be hit since the previous prompt validates the choice. raise Exception(f"Unrecognized action: { action }")
async def final_step(self, step_context: WaterfallStepContext): try_another = step_context.result if try_another: return await step_context.replace_dialog(self.initial_dialog_id) return DialogTurnResult(DialogTurnStatus.Complete)
async def final_step(self, step_context: WaterfallStepContext): try_another = step_context.result if try_another: return await step_context.replace_dialog(self.initial_dialog_id) self._update_tracker.pop(step_context.context.activity.conversation.id) return DialogTurnResult(DialogTurnStatus.Complete)
async def _on_message_activity( self, step_context: WaterfallStepContext ) -> DialogTurnResult: """ This method just gets a message activity and runs it through LUIS. """ activity = step_context.context.activity if not self._luis_recognizer.is_configured: await step_context.context.send_activity( MessageFactory.text( "NOTE: LUIS is not configured. To enable all capabilities, add 'LuisAppId', 'LuisAPIKey' and" " 'LuisAPIHostName' to the config.py file.", input_hint=InputHints.ignoring_input, ) ) else: # Call LUIS with the utterance. luis_result = await self._luis_recognizer.recognize(step_context.context) message = f'LUIS results for "{activity.Text}":\n' intent, intent_score = None, None if luis_result.intents: max_value_key = max( luis_result.intents, key=lambda key: luis_result.intents[key] ) intent, intent_score = max_value_key, luis_result.intents[max_value_key] message += f'Intent: "{intent}" Score: {intent_score}\n' await step_context.context.send_activity( MessageFactory.text(message, input_hint=InputHints.ignoring_input,) ) # Start a dialog if we recognize the intent. top_intent = luis_result.get_top_scoring_intent().intent if top_intent == "BookFlight": return await self._begin_book_flight(step_context) if top_intent == "GetWeather": return await self._begin_get_weather(step_context) # Catch all for unhandled intents. didnt_understand_message_text = f"Sorry, I didn't get that. Please try asking in a different way (intent was {top_intent})" await step_context.context.send_activity( MessageFactory.text( didnt_understand_message_text, didnt_understand_message_text, input_hint=InputHints.ignoring_input, ) ) return DialogTurnResult(DialogTurnStatus.Complete)
async def final_step(self, step_context: WaterfallStepContext): try_another = step_context.result if try_another: return await step_context.replace_dialog(self.initial_dialog_id) await step_context.context.send_activity( Activity( type=ActivityTypes.end_of_conversation, code=EndOfConversationCodes.completed_successfully, )) return DialogTurnResult(DialogTurnStatus.Complete)
async def on_event_activity(self, step_context: WaterfallStepContext): activity = step_context.context.activity await step_context.context.send_activity( Activity( type=ActivityTypes.trace, timestamp=datetime.utcnow(), name="ActivityRouterDialog.on_event_activity()", label= f"Name: {activity.name}. Value: {json.dumps(activity.value)}", )) if activity.name == "Cards": return await step_context.begin_dialog(CardDialog.__name__) if activity.name == "Proactive": return await step_context.begin_dialog( WaitForProactiveDialog.__name__) if activity.name == "MessageWithAttachment": return await step_context.begin_dialog( MessageWithAttachmentDialog.__name__) if activity.name == "Auth": return await step_context.begin_dialog(AuthDialog.__name__) if activity.name == "Sso": return await step_context.begin_dialog(SsoSkillDialog.__name__) if activity.name == "FileUpload": return await step_context.begin_dialog(FileUploadDialog.__name__) if activity.name == "Echo": # Start the EchoSkillBot message_activity = MessageFactory.text("I'm the echo skill bot") message_activity.delivery_mode = activity.delivery_mode dialog = await self.find_dialog(ECHO_SKILL) return await step_context.begin_dialog( dialog.id, BeginSkillDialogOptions(activity=message_activity)) if activity.name == "Delete": return await step_context.begin_dialog(DeleteDialog.__name__) if activity.name == "Update": return await step_context.begin_dialog(UpdateDialog.__name__) # We didn't get an event name we can handle. await step_context.context.send_activity( activity_or_text= f'Unrecognized EventName: "{step_context.context.activity.name}".', input_hint=InputHints.ignoring_input, ) return DialogTurnResult(DialogTurnStatus.Complete)
async def interrupt(self, inner_dc: DialogContext) -> DialogTurnResult: if inner_dc.context.activity.type == ActivityTypes.message: text = inner_dc.context.activity.text.lower() if text == 'help' or text == '?': await inner_dc.context.send_activity("Show Help...") return DialogTurnResult(DialogTurnStatus.Waiting) if text == 'cancel' or text == 'quit': await inner_dc.context.send_activity("Cancelling") return await inner_dc.cancel_all_dialogs() return None
async def _insert_info( self, step_context: WaterfallStepContext) -> DialogTurnResult: # uses adaptive cards to insert data step_context.values.update(step_context.options) message = Activity( text="Compila la seguente scheda", type=ActivityTypes.message, attachments=[INSERT_PERSON_CARD], ) await step_context.context.send_activity(message) return DialogTurnResult(status=DialogTurnStatus.Waiting, result={})
async def interrupt(self, inner_dc: DialogContext) -> DialogTurnResult: """Detect interruptions.""" if inner_dc.context.activity.type == ActivityTypes.message: text = inner_dc.context.activity.text.lower() if text in ("help", "?"): await inner_dc.context.send_activity("Show Help...") return DialogTurnResult(DialogTurnStatus.Waiting) if text in ("cancel", "quit"): await inner_dc.context.send_activity("Cancelling") return await inner_dc.cancel_all_dialogs() return None
async def first_step( self, step_context: WaterfallStepContext) -> DialogTurnResult: """Prompt for destination.""" card_details = step_context.options food_card = self.create_adaptive_card_attachment() response = self.create_response(step_context.context.activity, food_card) await step_context.context.send_activity(response) await step_context.context.send_activity('Card') if step_context.context.activity.value is None: return DialogTurnResult(DialogTurnStatus.Waiting) return await step_context.next(card_details)
async def handle_update_dialog_step(self, step_context: WaterfallStepContext): channel = step_context.context.activity.channel_id if channel in self._update_supported: if step_context.context.activity.conversation.id in self._update_tracker: conversation_id = step_context.context.activity.conversation.id tracked_tuple = self._update_tracker[conversation_id] activity = MessageFactory.text( f"This message has been updated {tracked_tuple.item2} time(s)." ) tracked_tuple.item2 += 1 activity.id = tracked_tuple.item1 self._update_tracker[conversation_id] = tracked_tuple await step_context.context.update_activity(activity) else: response = await step_context.context.send_activity( MessageFactory.text("Here is the original activity.")) self._update_tracker[ step_context.context.activity.conversation.id] = ( response.id, 1, ) else: await step_context.context.send_activity( MessageFactory.text( f"Delete is not supported in the {channel} channel.")) await step_context.context.send_activity( Activity( type=ActivityTypes.end_of_conversation, code=EndOfConversationCodes.completed_successfully, )) return DialogTurnResult(DialogTurnStatus.Complete) # Ask if we want to update the activity again. message_text = "Do you want to update the activity again?" reprompt_message_text = "Please select a valid answer" options = PromptOptions( prompt=MessageFactory.text(message_text, message_text), retry_prompt=MessageFactory.text(reprompt_message_text, reprompt_message_text), ) return await step_context.prompt(ConfirmPrompt.__name__, options)
async def handle_delete_dialog_step(self, step_context: WaterfallStepContext): channel = step_context.context.activity.channel_id if channel in self._delete_supported: response = await step_context.context.send_activity( MessageFactory.text("I will delete this message in 5 seconds")) time.sleep(5) await step_context.context.delete_activity(response.id) else: await step_context.context.send_activity( MessageFactory.text( f"Delete is not supported in the {channel} channel.")) return DialogTurnResult(DialogTurnStatus.Complete)
async def _begin_get_weather( self, step_context: WaterfallStepContext ) -> DialogTurnResult: activity = step_context.context.activity location = Location() if activity.value: location.from_json(activity.value) # We haven't implemented the GetWeatherDialog so we just display a TODO message. get_weather_message = f"TODO: get weather for here (lat: {location.latitude}, long: {location.longitude}" await step_context.context.send_activity( MessageFactory.text( get_weather_message, get_weather_message, InputHints.ignoring_input, ) ) return DialogTurnResult(DialogTurnStatus.Complete)
async def interrupt(self, inner_dc: DialogContext) -> DialogTurnResult: """Detect interruptions.""" if inner_dc.context.activity.type == ActivityTypes.message: text = inner_dc.context.activity.text.lower() if text == "help" or text == "?": await inner_dc.context.send_activity("Show Help...") return DialogTurnResult(DialogTurnStatus.Waiting) if text == "cancel" or text == "quit": await inner_dc.context.send_activity("Cancelling") return await inner_dc.cancel_all_dialogs() if text == "menu": await inner_dc.context.send_activity(MessageFactory.text('Возврат меню')) return await inner_dc.cancel_all_dialogs() return None
async def _on_event_activity( self, step_context: WaterfallStepContext) -> DialogTurnResult: activity = step_context.context.activity # Resolve what to execute based on the event name. if activity.name == "BookFlight": return await self._begin_book_flight(step_context) if activity.name == "GetWeather": return await self._begin_get_weather(step_context) # We didn't get an activity name we can handle. await step_context.context.send_activity( MessageFactory.text( f'Unrecognized ActivityName: "{activity.name}".', input_hint=InputHints.ignoring_input, )) return DialogTurnResult(DialogTurnStatus.Complete)
async def __check_for_multiturn_prompt(self, step_context: WaterfallStepContext): dialog_options: QnAMakerDialogOptions = ObjectPath.get_path_value( step_context.active_dialog.state, QnAMakerDialog.KEY_OPTIONS ) response = step_context.result if response and isinstance(response, List): answer = response[0] if answer.context and answer.context.prompts: previous_context_data = ObjectPath.get_path_value( step_context.active_dialog.state, QnAMakerDialog.KEY_QNA_CONTEXT_DATA, {}, ) for prompt in answer.context.prompts: previous_context_data[prompt.display_text] = prompt.qna_id ObjectPath.set_path_value( step_context.active_dialog.state, QnAMakerDialog.KEY_QNA_CONTEXT_DATA, previous_context_data, ) ObjectPath.set_path_value( step_context.active_dialog.state, QnAMakerDialog.KEY_PREVIOUS_QNA_ID, answer.id, ) ObjectPath.set_path_value( step_context.active_dialog.state, QnAMakerDialog.KEY_OPTIONS, dialog_options, ) # Get multi-turn prompts card activity. message = QnACardBuilder.get_qna_prompts_card( answer, dialog_options.response_options.card_no_match_text ) await step_context.context.send_activity(message) return DialogTurnResult(DialogTurnStatus.Waiting) return await step_context.next(step_context.result)
async def process_activity(self, step_context: WaterfallStepContext): # A skill can send trace activities, if needed. await step_context.context.send_activity( Activity( type=ActivityTypes.trace, timestamp=datetime.utcnow(), name="ActivityRouterDialog.process_activity()", label=f"Got ActivityType: {step_context.context.activity.type}", )) if step_context.context.activity.type == ActivityTypes.event: return await self.on_event_activity(step_context) # We didn't get an activity type we can handle. await step_context.context.send_activity( activity_or_text= f'Unrecognized ActivityType: "{step_context.context.activity.type}".', input_hint=InputHints.ignoring_input, ) return DialogTurnResult(DialogTurnStatus.Complete)
async def interrupt(self, inner_dc: DialogContext) -> DialogTurnResult: if inner_dc.context.activity.type == ActivityTypes.message: text = inner_dc.context.activity.text.lower() help_message = Activity( type=ActivityTypes.message, attachments=[CardFactory.adaptive_card(Cards.help_card)], ) if text in ("help", "?"): await inner_dc.context.send_activity(help_message) return DialogTurnResult(DialogTurnStatus.Waiting) cancel_message_text = "Cancelled." cancel_message = MessageFactory.text( cancel_message_text, cancel_message_text, InputHints.ignoring_input ) if text in ("cancel", "quit", "exit"): await inner_dc.context.send_activity(cancel_message) return await inner_dc.cancel_all_dialogs() return None
async def process_activity( self, step_context: WaterfallStepContext) -> DialogTurnResult: current_activity_type = step_context.context.activity.type # A skill can send trace activities, if needed. await step_context.context.send_trace_activity( f"{ActivityRouterDialog.__name__}.process_activity()", label=f"Got ActivityType: {current_activity_type}", ) if current_activity_type == ActivityTypes.event: return await self._on_event_activity(step_context) if current_activity_type == ActivityTypes.message: return await self._on_message_activity(step_context) else: # We didn't get an activity type we can handle. await step_context.context.send_activity( MessageFactory.text( f'Unrecognized ActivityType: "{current_activity_type}".', input_hint=InputHints.ignoring_input, )) return DialogTurnResult(DialogTurnStatus.Complete)
async def interrupt(self, inner_dc: DialogContext) -> DialogTurnResult: LOGGER.debug(msg=f"{CancelAndHelpDialog.__name__}: interrupt") if inner_dc.context.activity.type == ActivityTypes.message: text = inner_dc.context.activity.text.lower() message = Activity( type=ActivityTypes.message, attachments=[CardFactory.adaptive_card(HelpCard)]) if text in (Prompts.HELP.value, Prompts.QUESTION_MARK.value): await inner_dc.context.send_activity(message) return DialogTurnResult(DialogTurnStatus.Waiting) if text in (Prompts.CANCEL.value, Prompts.END.value, Prompts.QUIT.value): cancel_message = MessageFactory.text(messages.CANCELLED, messages.CANCELLED, InputHints.ignoring_input) await inner_dc.context.send_activity(cancel_message) await inner_dc.cancel_all_dialogs() return await inner_dc.replace_dialog(self.initial_dialog_id) return None
async def interrupt(self, inner_dc: DialogContext) -> DialogTurnResult: if inner_dc.context.activity.type == ActivityTypes.message: text = inner_dc.context.activity.text.lower() help_message_text = "Show Help..." help_message = MessageFactory.text(help_message_text, help_message_text, InputHints.expecting_input) if text in ("help", "?"): await inner_dc.context.send_activity(help_message) return DialogTurnResult(DialogTurnStatus.Waiting) cancel_message_text = "Cancelling" cancel_message = MessageFactory.text(cancel_message_text, cancel_message_text, InputHints.ignoring_input) if text in ("cancel", "quit"): await inner_dc.context.send_activity(cancel_message) return await inner_dc.cancel_all_dialogs() return None
async def interrupt(self, inner_dc: DialogContext) -> DialogTurnResult: if inner_dc.context.activity.type == ActivityTypes.message: text = inner_dc.context.activity.text.lower() help_message_text = "Please tell me the Azure AI service/area. We will find their PM/Dev contact for you." help_message = MessageFactory.text( help_message_text, help_message_text, InputHints.expecting_input ) if text in ("help", "?"): await inner_dc.context.send_activity(help_message) return DialogTurnResult(DialogTurnStatus.Waiting) cancel_message_text = "Cancelling" cancel_message = MessageFactory.text( cancel_message_text, cancel_message_text, InputHints.ignoring_input ) if text in ("cancel", "quit", "exit", 'bye'): await inner_dc.context.send_activity(cancel_message) return await inner_dc.cancel_all_dialogs() return None
async def interrupt(self, inner_dc: DialogContext) -> DialogTurnResult: if inner_dc.context.activity.type == ActivityTypes.message: text = inner_dc.context.activity.text.lower() help_message_text = "Sono un bot dotato di intelligenza artificiale che ti permette di:\n\n- Ricercare libri e mostrarti i prezzi migliori sul mercato.\n- Creare una wishlist dove poter inserire tutti i libri che ti interessano.\n- Mantenere sott'occhio i libri della tua wishlist e avvisarti se cambiano di prezzo, o ritornano disponibili.\n- Posso offrirti suggerimenti su nuovi libri da leggere in base alle tue preferenze.\n- Posso guidarti all'acquisto di nuovi libri, confrontando le varie recensioni per un particolare libro che ti interessa.\n\nPuoi utilizzarmi come preferisci, puoi impartirmi comandi, oppure utilizzare i bottoni del menu. " help_message = MessageFactory.text(help_message_text, help_message_text, InputHints.expecting_input) if text.lower() in ("help", "?"): await inner_dc.context.send_activity(help_message) return DialogTurnResult(DialogTurnStatus.Waiting) cancel_message_text = "Cancelling" cancel_message = MessageFactory.text(cancel_message_text, cancel_message_text, InputHints.ignoring_input) if text.lower() in ("cancel", "quit"): await inner_dc.context.send_activity(cancel_message) return await inner_dc.cancel_all_dialogs() return None
async def display_card_step(self, step_context: WaterfallStepContext): if step_context.context.activity.value is not None: await self.handle_special_activity(step_context) else: # Check to see if the activity is an adaptive card or a bot action response card_type = CardOptions(step_context.result.value) if ChannelSupportedCards.is_card_supported( step_context.context.activity.channel_id, card_type): if card_type == CardOptions.ADAPTIVE_CARD_BOT_ACTION: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_adaptive_card_bot_action()) ) elif card_type == CardOptions.ADAPTIVE_CARD_TEAMS_TASK_MODULE: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_adaptive_card_task_module( ))) elif card_type == CardOptions.ADAPTIVE_CARD_SUBMIT_ACTION: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_adaptive_card_submit())) elif card_type == CardOptions.HERO: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_hero_card())) elif card_type == CardOptions.THUMBNAIL: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_thumbnail_card())) elif card_type == CardOptions.RECEIPT: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_receipt_card())) elif card_type == CardOptions.SIGN_IN: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_signin_card())) elif card_type == CardOptions.CAROUSEL: # NOTE if cards are NOT the same height in a carousel, # Teams will instead display as AttachmentLayoutTypes.List await step_context.context.send_activity( MessageFactory.carousel([ CardSampleHelper.create_hero_card(), CardSampleHelper.create_hero_card(), CardSampleHelper.create_hero_card(), ])) elif card_type == CardOptions.LIST: await step_context.context.send_activity( MessageFactory.list([ CardSampleHelper.create_hero_card(), CardSampleHelper.create_hero_card(), CardSampleHelper.create_hero_card(), ])) elif card_type == CardOptions.O365: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_o365_connector_card())) elif card_type == CardOptions.TEAMS_FILE_CONSENT: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_teams_file_consent_card( TEAMS_LOGO_FILE_NAME))) elif card_type == CardOptions.ANIMATION: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_animation_card( MIND_BLOWN_GIF))) elif card_type == CardOptions.AUDIO: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_audio_card( f"{self.configuration.SERVER_URL}/{MUSIC_API}") )) elif card_type == CardOptions.VIDEO: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_video_card( CORGI_ON_CAROUSEL_VIDEO))) elif card_type == CardOptions.ADAPTIVE_UPDATE: await step_context.context.send_activity( MessageFactory.attachment( CardSampleHelper.create_adaptive_update_card())) elif card_type == CardOptions.END: # End the dialog so the host gets an EoC await step_context.context.send_activity( Activity( type=ActivityTypes.end_of_conversation, code=EndOfConversationCodes.completed_successfully, )) return DialogTurnResult(DialogTurnStatus.Complete) else: await step_context.context.send_activity( f"{card_type.value} cards are not supported in the " f"{step_context.context.activity.channel_id} channel.") return await step_context.replace_dialog(self.initial_dialog_id, "What card would you want?")
async def __call_generate_answer(self, step_context: WaterfallStepContext): dialog_options: QnAMakerDialogOptions = ObjectPath.get_path_value( step_context.active_dialog.state, QnAMakerDialog.KEY_OPTIONS ) # Resetting context and QnAId dialog_options.options.qna_id = 0 dialog_options.options.context = QnARequestContext() # Storing the context info step_context.values[ QnAMakerDialog.PROPERTY_CURRENT_QUERY ] = step_context.context.activity.text # -Check if previous context is present, if yes then put it with the query # -Check for id if query is present in reverse index. previous_context_data = ObjectPath.get_path_value( step_context.active_dialog.state, QnAMakerDialog.KEY_QNA_CONTEXT_DATA, {} ) previous_qna_id = ObjectPath.get_path_value( step_context.active_dialog.state, QnAMakerDialog.KEY_PREVIOUS_QNA_ID, 0 ) if previous_qna_id > 0: dialog_options.options.context = QnARequestContext( previous_qna_id=previous_qna_id ) current_qna_id = previous_context_data.get( step_context.context.activity.text ) if current_qna_id: dialog_options.options.qna_id = current_qna_id # Calling QnAMaker to get response. qna_client = self._get_qnamaker_client(step_context) response = await qna_client.get_answers_raw( step_context.context, dialog_options.options ) is_active_learning_enabled = response.active_learning_enabled step_context.values[QnAMakerDialog.PROPERTY_QNA_DATA] = response.answers # Resetting previous query. previous_qna_id = -1 ObjectPath.set_path_value( step_context.active_dialog.state, QnAMakerDialog.KEY_PREVIOUS_QNA_ID, previous_qna_id, ) # Check if active learning is enabled and send card # maximum_score_for_low_score_variation is the score above which no need to check for feedback. if ( response.answers and response.answers[0].score <= self.maximum_score_for_low_score_variation ): # Get filtered list of the response that support low score variation criteria. response.answers = qna_client.get_low_score_variation(response.answers) if len(response.answers) > 1 and is_active_learning_enabled: suggested_questions = [qna.questions[0] for qna in response.answers] message = QnACardBuilder.get_suggestions_card( suggested_questions, dialog_options.response_options.active_learning_card_title, dialog_options.response_options.card_no_match_text, ) await step_context.context.send_activity(message) ObjectPath.set_path_value( step_context.active_dialog.state, QnAMakerDialog.KEY_OPTIONS, dialog_options, ) await qna_client.close() return DialogTurnResult(DialogTurnStatus.Waiting) # If card is not shown, move to next step with top qna response. result = [response.answers[0]] if response.answers else [] step_context.values[QnAMakerDialog.PROPERTY_QNA_DATA] = result ObjectPath.set_path_value( step_context.active_dialog.state, QnAMakerDialog.KEY_OPTIONS, dialog_options ) await qna_client.close() return await step_context.next(result)