one pattern multiple responses in aiml - chat

I want to make a chatbot,so my doubt is how can i respond in multiple ways for a single pattern in aiml ?
for example if the user asks whats next the chat bot should respond step1
if again he asks whats next it should respond step2.

You can use "that" tags in the template, which remember the last bot statement and answer accordingly, although this gives you just one level of control. If you want more levels, a better way is to set topics using the "think" tags, and then defining topic specific templates which will be used first.

To have multiple responses for a single <pattern>, you can use the <random> and <li> tags:
<category>
<pattern>WHATS NEXT</pattern>
<template><random>
<li>Step 1</li>
<li>Step 2</li>
</random></template>
</category>
However, the responses will be generated randomly and not in a certain order.
For instance, if the user inputs "What's next?" for the first time, the response might be "Step 1" and the next time the user inputs the same keyword, the response might still be "Step 1".

First you need a category that knows the steps, and returns the answer in a defined format. In my example the format is
MAKE TOAST STEP * *
where the first star is the step number and the second star represents the remainder of the returned text. Here is the category:
<category>
<pattern>MAKING TOAST STEP *</pattern>
<template>
<set var="step"><star/></set>
<condition var="step">
<li value="1">Make toast step 1, get some bread</li>
<li value="2">Make toast step 2, put the bread in the toaster</li>
<li value="3">Make toast step 3, wait until it pops up</li>
<li>Make toast step 4, eat the toast</li>
</condition>
</template>
</category>
Then you need a category that calls the next step but only if the previous answer was a toast-making question. This category uses the that tag to ensure it is activated only during the toast making conversation. It uses thatstar to get the previous step number, then adds one to the step number:
<category>
<pattern>WHAT IS NEXT</pattern>
<that>MAKE TOAST STEP * *</that>
<template>
<set var="step"><calculate><thatstar/>+1</calculate></set>
<srai>MAKING TOAST STEP <get var="step"/></srai>
</template>
</category>
Then you need a category to kick off the whole sequence:
<category>
<pattern>HOW DO I MAKE TOAST</pattern>
<template>
<srai>MAKING TOAST STEP 1</srai>
</template>
</category>
The caveats with this approach are (1) it uses the calculate tag which is not standard AIML but should be coded quite easily. (2) It uses AIML v2 elements such as variables used with get and set. (3) I have not tested it, but I am confident the process should work.

<category>
<pattern>TEST SPLIT</pattern>
<template>
I don't want to talk about that now.
<split/>
I would rather talk about you.
</template>
</category>
Do <split/>
Output
Reference

Related

AIML How to get out of topic from underscored wildcard

In aiml how to get out of topic which has underscored wildcard. Here is the code
<category>
<pattern>TOPIC</pattern>
<template>ok <think><set name="topic">ctt</set></think></template>
</category>
<topic name="ctt">
<category>
<pattern>_</pattern>
<template>no</template>
</category>
<category>
<pattern>CHANGE TOPIC</pattern>
<template>YES <set name="topic"></set></template>
</category>
</topic>
The output is
Human: TOPIC
Robot: ok
Human: CSA
Robot: no
Human: CHANGE TOPIC
Robot: no
How to fix it without using conditions?
The reason for this is that the underscore wildcard takes priority over everything else, even a direct match.
Hopefully, you are using AIML 2 rather than AIML 1 and so you can simply change the <pattern>CHANGE TOPIC</pattern> to <pattern>$CHANGE TOPIC</pattern>.
The dollar wildcard means if your input exactly matches the pattern, the template will be activated.
If you are not using AIML 2, I would have to ask why, but if for whatever reason you are not, you will need a condition tag to do the same action. Swap your underscore category for this one instead. It checks the input and if it matches CHANGE TOPIC, the topic is reset.
<category>
<pattern>_</pattern>
<template>
<think><set var="userinput"><star/></set></think>
<condition var="userinput">
<li value="CHANGE TOPIC">YES <set name="topic"></set></li>
<li>no</li>
</condition>
</template>
</category>

How can I create a chatbot that organizes input into selected templates?

I want to create a chatbot that asks questions that, according to their answers, travel down a tree of templates. I'm not very experienced in the coding world, so excuse me if my jargon isn't right!
Here's an example.
I want to write custom reports based on a user's input into a chatbot. Let's imagine the user wants some daily, custom motivation.
How are you feeling today?
Based on user inputs this is categorized into:
"GOOD - BAD - SAD - HAPPY - EXCITED" etc...
Depending on which one, we travel down a "template tree," so any templates that would exist under the "BAD" category are disregarded if the user writes "Pretty Good" and it's categorized as "Good."
Then we ask questions like, "What's your name?", that are stored as variables to incorporate into a text template once we find the right template based on their inputs.
What's the best platform to build this? Is it indeed a chatbot?
Thank you so much for the help!
I tried Pandorabots but it seems too linear - as in a input > response model, there's not much conditional logic. I'm ready to research and learn, so any tips on which platform / approach would be very helpful!
Pandorabots uses AIML to create a chatbot and you can certainly do conditional logic in it. Here's some code that will solve your request:
<?xml version="1.0" encoding="UTF-8"?>
<aiml version="2.0">
<category>
<pattern>HI</pattern>
<template>
Hi there. What is your name?
</template>
</category>
<category>
<pattern>*</pattern>
<that>WHAT IS YOUR NAME</that>
<template>
<think><set name="name"><star/></set></think>
How are you feeling today?
</template>
</category>
<category>
<pattern>*</pattern>
<that>HOW ARE YOU FEELING TODAY</that>
<template>
<think><set name="mood"><star/></set></think>
<condition name="mood">
<li value="good">That's great <get name="name"/>.</li>
<li value="bad">Sorry to hear that <get name="name"/>. Can I help?</li>
<li value="sad">Cheer up <get name="name"/>, it's a beautiful day!</li>
<li value="happy">Oh wow <get name="name"/>. I'm so pleased for you!</li>
<li value="excited">Amazing <get name="name"/>! What's happened?</li>
<li>The day is yours to command <get name="name"/>.</li>
</condition>
</template>
</category>
</aiml>
A sample conversation would look like this:
Using the pattern side tag, you can also do this with Pandorabots to group similar answers together. Create sets called "good" and "bad" with all the emotions that should trigger the templates. Example of the "good" set:
[
["amazing"],
["good"],
["happy"],
["great"]
]
And then use a categories like this:
<category>
<pattern>I FEEL <set>good</set></pattern>
<template>Great to hear!</template>
</category>
<category>
<pattern>I FEEL <set>bad</set></pattern>
<template>Sorry to hear that. Can I help?</template>
</category>
Hope that helps. Pandorabots is capable of FAR more than input - response and I've won the Loebner Prize 4 times for having the world's most humanlike conversational AI using AIML and Pandorabots.
Since you already tried Pandorabots then I assume you are familiar with XML and aiml, that's why I am proposing program O Program O on Github
aiml has a functionality call which can be used to build interactive tree chats.
check my example below. though I guess you might have come across aiml in your research.
<?xml version = "1.0" encoding = "UTF-8"?>
<aiml version = "1.0.1" encoding = "UTF-8"?>
<category>
<pattern>hi</pattern>
<template>How are you feeling today?</template>
</category>
<category>
<pattern>GOOD</pattern>
<that>How are you feeling today?</that>
<template>Nice, I like it that way.</template>
</category>
<category>
<pattern>BAD</pattern>
<that>How are you feeling today?</that>
<template>
<randon>
<li>Ok! I think you need an appointment with a doctor?</li
<li>How exactly are you feeling?</li>
</random>
</template>
</category>
<category>
<pattern>SAD_</pattern>
<that>How are you feeling today?</that>
<template>
<randon>
<li>Ok! what happened?</li
<li>how can i help?</li>
</random>
</template>
</category>
<category>
<pattern>HAPPY_</pattern>
<that>How are you feeling today?</that>
<template>
<randon>
<li>great! its good for you</li
<li>thats what up.</li>
</random>
</template>
</category>
</aiml>

Locators combination

I am working on protractor to test the AngularJs application. Here I came across one scenario where I want to click on image for different users. But the id for image is same for all (say 10) users. So I found one more element that is one unique number allocated to each user. The code for 2 different users are:
USER1:
img id="searchPatientImgAdmittedM" class="img-circle picwidth" ng-click="getPatientVitalLabPharmacy(patient.patientId._id)" onclick="ShowHide(this)" src="icons/male.png" alt="" role="button" tabindex="0"
span class="clearfloat ng-binding">12339/span
USER2:
img id="searchPatientImgAdmittedM" class="img-circle picwidth" ng-click="getPatientVitalLabPharmacy(patient.patientId._id)" onclick="ShowHide(this)" src="icons/male.png" alt="" role="button" tabindex="0"
span class="clearfloat ng-binding">8841/span
EDIT:
The full HTML code
<div class="col-md-10 col-sm-9 col-xs-9 skin-font-color paddingTop7">
<span class="skin-font-color">
<span class="name clearfloat ng-binding">KRISHA</span>
<span class="clearfloat ng-binding">12348</span>
<img id="searchPatientImgAdmittedF" class="img-circle picwidth" ng-click="getPatientVitalLabPharmacy(patient.patientId._id)" onclick="ShowHide(this)" src="icons/femaleImages.jpg" alt="" role="button" tabindex="0">
</div>
I tried to do :
element(by.id('searchPatientImgAdmittedF')).all(by.tagName('‌​12348')).click();
// or
element(by.id('searchPatientImgAdmittedF')).element(by.tagNa‌​me('12348')).click()‌​;
How can I make combination of locators to click on this users. Only image part is clickable.
Thanks four your additions.
Now you're trying to click on a sister-element. There are several approaches to do so.
The one I'm usually using is:
element(by.cssContainingText('span.clearfloat','12348')).element(by.xpath('..')).$('#searchPatientImgAdmittedF').click();
//equal to
element(by.cssContainingText('span.clearfloat','12348')).element(by.xpath('..')).element(by.id('searchPatientImgAdmittedF')).click();
This evaluates first the identifiable tag with the unique number, then climbs up to its parent element, then from there gets the img-element with the ID.
The $() selector
The cssContainingText() selector
Another option would be to use isElementPresent(), which evaluates the existence of a child-element. However, the code is (from my point of view) more complex and I don't see, how cssContainingText() could be used there, so I don't try to do it here.
Thanks for your quick help in solving my issue. I want to add here that I found the answer to my problem and now I am able to click on the particular user I want from the list of many users. The code I am using is :
element(by.cssContainingText('span.clearfloat','12339'))
.element(by.xpath('/html/body/div[3]/div[1]/div[17]/div/div/table[4]/tbody/tr[3]/td[1]/div[1]/img'))
.click();
This is finding the child element first and then the parent element.The id was all same for all the users so it was not taking that and so I used only xpath along with unique number.
Thanks again for the help.

Umbraco - Displaying a specific image within a macro for-each child of certain node

Umbraco newbie here. I've researched a tonne but can't seem to find what I' looking for.
I have a site with a slider on the homepage, the slider is sitting in a macro which is using a for-each (of a nodes children) with a final goal to display the 'heroImage' image from that doctype. I cant post images as a newbie to this site, but heres my content structure:
HOME
PORTFOLIO
- First Item
- Another Item
ABOUT
CONTACT US
Home, Portfolio, ABOUT and CONTACT US are "Landing Pages" document types, and the children under Portfolio (First Item and Another Item) are "Portfolio Entries" document types. Below is the code on "Landing Page" calling the Slideshow macro.
Portfolio Entry has fields:
heroImage
images
body
Slideshow macro obviously being the highlight there. Easy enough. Heres my macro code where you'll see I'm trying to display the heroImage of the node in question for each 'for-each'.
<xsl:template match="/">
<!-- slider -->
<div id="slideshow">
<div id="slider" class="nivoSlider">
<xsl:for-each select="umbraco.library:GetXmlNodeById(1081)/*[#isDoc and position() < 4]">
<xsl:variable name="mediaId" select="umbraco.library:GetMedia(#id, 'false')/data [#alias = 'umbracoFile']" />
<xsl:if test="$mediaId > 0">
<xsl:variable name="mediaNode" select="umbraco.library:GetMedia($mediaId, 0)" />
<xsl:if test="count($mediaNode/data) > 0 and string($mediaNode/data[#alias='umbracoFile']) != ''">
<img src="{$mediaNode/data[#alias='umbracoFile']}" alt="[image]" />
</xsl:if>
</xsl:if>
</xsl:for-each>
</div>
</div>
<!-- data-transition="slideInLeft" -->
<script type="text/javascript">
$(window).load(function() {
$('#slider').nivoSlider();
});
</script>
</xsl:template>
I feel like im so close, and ran out of search queries as most of the solutions I found were dependant on the imageId being passed onto the macro from the other side of the macro which wouldn't work.
Hope Ive explained this enough and thanks in advance for your help!
First of all, it looks like you're hardcoding the parent node id. In the code you just provided, it seems to only be getting the children of the node with id 1081. From reading what you just posted, it would seem that on all landing pages, you want to display their individual portfolio entries.
Either way, I would stay away from hardcoding IDs. If the node id changes in any way(user deletes the node, it gets exported as a package to the live environment, etc), your code will stop working. I'd just use $currentPage instead.
Judging by your filter, I imagine you only want the first 3 items to show in the slider. The code seems correct, but you seem to be using the old schema and its associated xpath. If you're using a newer version of Umbraco, the way you reference node data in xslt would have changed. I would guess that you've found many code examples and tried merging them together, without realising they wouldn't call the same schema.
This wiki link will provide more information, and hopefully fix your problem if you're using the wrong xpath.

Adding items to a resource restfully using OpenRasta

I'm using OpenRasta to create a Survey application.
I have a SurveyResource that is accessible at /surveys/{id} and editable at /surveys/{id}/edit
I'd now like to add questions to the survey, as that is the point of a survey, but I'm not sure what the most restful way of doing this is and how to set it up in OR.
I'm thinking I should have a QuestionResource (that has details of the question type, question text, etc) and it should be posted to /surveys/{id}/questions and handled by a question handler, but I can't work out how to configure OR.
I've pushed my project onto github at https://github.com/oharab/OpenSurvey/tree/add_question_to_survey
Can anyone help me?
Ben
it depends on the way you want to model your resources. It's perfectly possible that you'd never explicitly provide access to a single question, and would modify the entire survey document, like so:
PUT /surveys/123
<survey>
<link rel="update" href="/surveys/123" method="PUT"
type="application/vnd.mycorp.survey+xml" />
<question id="age">
<label>How old are you?</label>
<select>
<option>0 - 5</option>
<option>6 - 10</option>
<option>10 - 13</option>
</select>
</question>
</survey>
If you go this route, you could even use HTML, or HTML 5 for your content so it's easy to consume by clients. Now you're just modifying the entire survey document at once.
Alternatively, you might want to separately address each question, giving them an individual URI, which I think is what you're talking about, like so:
GET /survey/123
<survey>
<link rel="add-question" href="/survey/123/questions"
type="application/vnd.mycorp.surveyquestion+xml" method="POST" />
<question>
<link rel="delete" href="/questions/123-age" method="DELETE" />
<link rel="update" href="/questions/123-age" type="application/vnd.mycorp.surveyquestion+xml" method="PUT" />
<label>How old are you?</label>
<select>
<option>0 - 5</option>
<option>6 - 10</option>
<option>10 - 13</option>
</select>
</question>
</survey>
Neither of these is more RESTful than the other, the difference is only in granularity of call. If you need the granularity of the latter, then configure yourself a separate handler per resource as in
using(OpenRastaConfiguration.Manual)
{
ResourceSpace.Has.ResourcesOfType<Survey>().AtUri("/survey/{id}").HandledBy<SurveyHandler>();
ResourceSpace.Has.ResourcesOfType<Question>().AtUri("/questions/{id}").HandleBy<QuestionHandler>();
}