The DialogFlow documentation writes that the base WelcomeDefaultIntent is triggered either by matching training phrases or every time the user starts a dialogue. But this is not true. If the user's phrases match one of the training phrases of another intent, this intent is triggered, instead of a WelcomeIntent. As a result, the user does not understand that he is communicating with the bot and the quality of service fall down. Please, give a hint, how to make the DefaultWelcomeIntent always works first when the user starts a dialogue, no matter what he wrote. I hope on you
That is an expected behavior. As the documentation mentions:
The default welcome intent is matched in one of two ways:
One of its training phrases are matched, which are pre-populated with
common greetings, like "hello".
This intent has a welcome event
attached to it, which is triggered when the end-user begins a
conversation with your agent via a supported integration.
However, it doesn't specify that no other intents can be matched at the beginning of a conversation. At the end of the day, the default welcome intent is just another intent that is automatically created alongside the agent, and pre-populated with training phrases. Intents will always "compete" with each other's matching phrases, so the best intent gets selected according to the user input, regardless of whether the intent is the welcome default intent or not.
From a natural conversational point of view, it doesn't makes much sense to "force" the welcome intent to always be triggered at the beginning of a conversation, regardless of the user input. An example could be:
User: What time is it?
Bot: It's 1:55 pm PT.
And you would be forcing this into something like:
User: What time is it?
Bot: Hey, my name is Bot, how can I help you?
User: What time is it?
Bot: It's 1:55 pm PT.
Adding an extra interaction for the user.
However, if you do want to force your welcome intent at the start of a conversation, or your use case requires to, you could try with:
Dialogflow Contexts, or.
Using the Detect Intent API method, which can receive a EventInput object that allow for matching intents by event name instead of the natural language input. Hence, you could use this to match the intent attached to the Welcome event, regardless of the user input.
Related
I'm bulding an agent with a lot of top level intents. Sometimes users ask a question which has not been added as an intent and it gets triggered by a wrong intent. Usually they try to ask the very same question again in a little different way. They get the same (wrong) intent again.
Is there a way I can avoid triggering the same intent multiple times in a row? It'd be cool to call the default fallback at the second time it is triggered. I'd like to apply this to all of the top level intents.
The way I would achieve this without fulfillment is a little clunky, but it will do the job. All you do is for every top-level intent, create a duplicate (with the same training phrases), named something like [original_intent_name]_repeat and put a input context required of [original_intent_name]_asked. Then for all your original top-level intents, add an output context of [original_intent_name]_asked with a lifespan of 1.
That way what happens is the following:
User: What's your name?
Bot: It's Dave! [intent `name`, output context `name_asked:1`
User: What's your name?
Bot: It appears you've already asked me my name! Try something else. [intent `name_repeat`]
This works because Dialogflow priorities intents with input context requirements over ones that do not.
I'm trying to build a basic "question/answer" app in Actions using DialogFlow. Right now I have two intents:
Intent 1: User says "Ask me a question" and the intent responds "Tell me about yourself"
Intent 2: I'd like to capture the user response to "tell me about yourself", but frankly there's no way to write enough training phrases to cover it.
I tried following this suggestion, and having Intent 1 send an output context called save_response and Intent 2 has an input context of save_response. Then for the training phrase I used #sys.any:save_response
When I try this action, it just invokes the default fallback intent every time. Thoughts on where I might be going wrong?
You need to create 2 intents, in the first intent your training phrase would be Ask me a question, output context will be save_response and response will be the question which you want to throw at the user.
Then in intent 2, you need to do following:
Set input context to save_response, so that it will only be
triggered when this is present in the contexts
Go to actions and parameters section and create a parameter named
answer, give entity type as #sys.any
Then go to training phrases section and add any training phrase, then
highlight it all, and select the parameter you just created
After that, your training phrases and entity section will be looking
like something like below image
Save the intent and you are done
Hope it helps.
In general, having an Intent with a training phrase that consists only of #sys.any may not always work as you expect.
Better would be to have a Fallback Intent that has the Input Context set to make sure you only capture things in that state (save_response in your case) and then to use the full text captured in your fulfillment.
When doing it this way, you do not need the "Intent 2" you described - or rather, this would be a Fallback Intent that you create in the Dialogflow UI. The Fallback Intent is triggered if no other Intent would match what the user has said.
To create a Fallback Intent, select the three dots in the upper right of the Dialogflow UI
then select "Create Fallback Intent"
The Fallback Intent editor is very similar to the normal Intent editor. The biggest difference is that the phrases you enter (and you don't need to enter any) will explicitly not match this Intent, and there are no parameters. Other aspects (the name, the Incoming Context, turning on fulfillment) are the same.
Let say I have 2 basic intents i.e Set Appointment and Cancel Appointment.
Each of the intents has its own follow up questions and so on. When the user is in the follow up chain for the intent, Set Appointment, I want to prevent the user from hopping to another intent if he/she says "cancel appointment for abc"
Since both intents have empty input contexts so they can be called from the Google Assistant's invocation i.e Tell XYZ App to set appointment for...., it seems that this allows the user to be able to hop between intent mid conversation.
How do I limit this behavior? Or is there some kind design best practices here?
First of all, remember that Intents represent what the user says, not what you're doing with that the user says.
Second, remember that users can change the course of the conversation at any time. So it makes sense that if they start adding an appointment, that they might want to cancel that appointment.
The best approach is that, if they try to cancel in the middle of making an appointment, you decide how you want to handle this change in conversation. And then just reply that way. You may choose to change tracks. Or you may choose to say something like "let's add this new appointment first, and then we can cancel the old one". With this scheme:
You have one Intent that matches "set the appointment for 10am"
In your handler:
If you aren't taking any action, you'd start prompting them for additional appointment setting info, or whatever.
If you are already setting an appointment, prompt them if they want to change the time to 10am
If you're cancelling an appointment, tell them that you'll talk about canceling the old one when you're done with the new one.
I tend to go with this approach in most (tho not all) cases. It lets me code the logic and lets me determine the best way to reply based on the entire state.
Another approach that you can use is to create an Intent with the Input Context that matches your current contextual line of questioning that matches the phrases from the Intent you don't want to match. (This might even be reasonable as part of a negative training phrase for a context-specific Fallback Intent.) Context matches are handled before context-free matches. So under this scheme you would have:
An Intent, without input context, that matches "set the appointment for 10am". The handler for this Intent would set the "set" context and start prompting for additional info.
An Intent, with your "set" input context, that matches "set the appointment for 10am". This could do something like re-start the prompting, or just change the time they're requesting.
An Intent, with your "cancel" input context, that matches "set the appointment for 10am". This handler would let them know that you'll ask about cancelling older appointments at the end.
Which method you use depends on how you're handling other state management in your code.
I have to train my dialogflow bot with a phrase i dont know i.e user can type anything he or she wants but i want that to work with a single intent only.
for example:
U- Good Morning
B- Morning how can i help you?
U- i want to create a ticket
B- Please provide a subject for the issue?
U- No i want to view a ticket with id ABC1234556
Now here bot should back track to another intent which will view the details related to the ticket id but thats not happening i am using dialogflow's system entity i.e #sys.any which captures anything user says. This entity captures anything and even back tracks on other intent's phrases like bye show all ticket's and etc but it just not works with this particular intent phrase!
I hope i have made clear what is bothering!
If you're using #sys.any in an intent to capture all user input after asking Please provide a subject for the issue, it won't be possible for another intent to be matched within Dialogflow.
To get around this issue, you could change your agent design, perhaps by confirming the "subject" in case the user wants to change path.
You could also try and match an intent to whatever text is captured by #sys.any, by calling Dialogflow's detectIntent endpoint from your webhook. However, this might result in unwanted behavior (e.g. if a legitimate ticket subject happened to match one of your intents).
I want to do some thing like this with api.ai. I am doing it as a telegram bot.
1st question: Tell me a joke?
Bot: Tells a joke ( picks it from text response that I specified )
2nd input from user: Some more.
Bot: It should tell another joke from the same list of responses.
One thing I could do is include MORE as a user input is joke intent and it would pick a response.
But I can not do this, because then even without asking 1st question if I give "more" as input it would pick a response from the list. Basically that wouldn't pick response based on context.
Any help onn the structure I should be using on api.ai to achieve something like this.
So the first intent where the user asks "tell me a joke?" sets an outgoing context- 'jokes'.
Follow-up intents for telling more jokes have 'jokes' for the incoming context, and, if you want to chain repeatable requests, set the outgoing context as 'jokes' as well.
If the user input like "tell me more" outside the 'jokes' context is still triggering the followup intent, either train your bot to recognize the difference, or create an explicit "tell me more" example in a fallback intent outside the jokes context.