Responding using rule-based matching with spaCy¶
Note
This tutorial requires ChatterBot 1.2.3 or newer.
ChatterBot includes logic adapters that support spaCy’s rule-based matching as a method for selecting responses to input statements. This functionality can be useful for cases where you need a chat bot to respond or carry out actions for specific inputs.
Matching phrase patterns¶
To get started we’ll need to set up a chat bot using the Specific Response Adapter (SpecificResponseAdapter
) class.
from chatterbot import ChatBot
chatbot = ChatBot(
'Example Bot',
logic_adapters=[
{
'import_path': 'chatterbot.logic.SpecificResponseAdapter',
'input_text': 'What is your name?',
'output_text': 'My name is ChatterBot.'
},
{
'import_path': 'chatterbot.logic.BestMatch',
'default_response': 'I am sorry, please try asking a different question.',
'maximum_similarity_threshold': 0.90
}
]
)
response = chatbot.get_response('What is your name?')
print(response)
response = chatbot.get_response('What is your purpose?')
print(response)
By default, the SpecificResponseAdapter
uses a case-sensitive exact match to determine if the input statement matches its defined input_text
value. Only when an exact match is found, will the response will be returned with a confidence of 1. Otherwise, the response will be returned with a confidence of 0, and the next logic adapter in the list will be used to select a response. In this case, the BestMatch
logic adapter is used as a fallback, configured with a predefined default_response
.
Matching an exact string is not always practical, in some cases for example it may be necessary to match a part or phrase pattern contained within a string of text. To achieve this, we can use spaCy’s rule-based matching to define a pattern that the input statement must match.
from chatterbot import ChatBot
from spacy.matcher import Matcher
# Pattern to match phrases close to "check if the website is up"
# and "check is the website is down"
pattern = [
{'LOWER': 'check'}, {}, {}, {'LOWER': 'website'}, {},
{'LEMMA': {'IN': ['up', 'down']}}
]
chatbot = ChatBot(
'Example Bot',
logic_adapters=[
{
'import_path': 'chatterbot.logic.SpecificResponseAdapter',
'matcher': Matcher,
'input_text': pattern,
'output_text': 'I will check the website status.'
},
{
'import_path': 'chatterbot.logic.BestMatch',
'default_response': 'I am sorry, please try asking a different question.',
'maximum_similarity_threshold': 0.90
}
]
)
response = chatbot.get_response('Check if the website is up')
print(response)
response = chatbot.get_response('Check if the website is down')
print(response)
Note
An alternative to the Matcher
class is the PhraseMatcher class, which can be used to match against a list of phrases (strings).
Calling a function in response to a match¶
In some cases, it may be necessary to call a function in response to a match. This can be achieved by defining a function that takes the input statement as an argument, and then passing that function to the output_text
parameter.
from chatterbot import ChatBot
from spacy.matcher import Matcher
def check_website_status():
from urllib.request import urlopen
HOSTNAME = 'https://docs.chatterbot.us/'
try:
urlopen(HOSTNAME)
return 'The website is up.'
except Exception:
return 'The website is down.'
pattern = [
{'LOWER': 'check'}, {}, {}, {'LOWER': 'website'}, {},
{'LEMMA': {'IN': ['up', 'down']}}
]
chatbot = ChatBot(
'Example Bot',
logic_adapters=[
{
'import_path': 'chatterbot.logic.SpecificResponseAdapter',
'matcher': Matcher,
'input_text': pattern,
'output_text': check_website_status
},
{
'import_path': 'chatterbot.logic.BestMatch',
'default_response': 'I am sorry, please try asking a different question.',
'maximum_similarity_threshold': 0.90
}
]
)
response = chatbot.get_response('Check if the website is up')
print(response)
response = chatbot.get_response('Check if the website is down')
print(response)