from __future__ import unicode_literals from chatter.chatterbot.logic import LogicAdapter class BestMatch(LogicAdapter): """ A logic adapter that returns a response based on known responses to the closest matches to the input statement. """ def get(self, input_statement): """ Takes a statement string and a list of statement strings. Returns the closest matching statement from the list. """ statement_list = self.chatbot.storage.get_response_statements() if not statement_list: if self.chatbot.storage.count(): # Use a randomly picked statement self.logger.info( 'No statements have known responses. ' + 'Choosing a random response to return.' ) random_response = self.chatbot.storage.get_random() random_response.confidence = 0 return random_response else: raise self.EmptyDatasetException() closest_match = input_statement closest_match.confidence = 0 # Find the closest matching known statement for statement in statement_list: confidence = self.compare_statements(input_statement, statement) if confidence > closest_match.confidence: statement.confidence = confidence closest_match = statement return closest_match def can_process(self, statement): """ Check that the chatbot's storage adapter is available to the logic adapter and there is at least one statement in the database. """ return self.chatbot.storage.count() def process(self, input_statement): # Select the closest match to the input statement closest_match = self.get(input_statement) self.logger.info('Using "{}" as a close match to "{}"'.format( input_statement.text, closest_match.text )) # Get all statements that are in response to the closest match response_list = self.chatbot.storage.filter( in_response_to__contains=closest_match.text ) if response_list: self.logger.info( 'Selecting response from {} optimal responses.'.format( len(response_list) ) ) response = self.select_response(input_statement, response_list) response.confidence = closest_match.confidence self.logger.info('Response selected. Using "{}"'.format(response.text)) else: response = self.chatbot.storage.get_random() self.logger.info( 'No response to "{}" found. Selecting a random response.'.format( closest_match.text ) ) # Set confidence to zero because a random response is selected response.confidence = 0 return response