<commit_before>from StringIO import StringIO
from os.path import dirname

import re
import requests
import wolframalpha
from six.moves import urllib

from mycroft.identity import IdentityManager
from mycroft.skills.core import MycroftSkill
from mycroft.util import CerberusAccessDenied
from mycroft.util.log import getLogger

__author__ = 'seanfitz'

logger = getLogger(__name__)


class EnglishQuestionParser(object):
    """
    Poor-man's english question parser. Not even close to conclusive, but appears to construct some decent w|a queries
    and responses.
    """

    def __init__(self):
        self.regexes = [
            re.compile(".*(?P<QuestionWord>who|what|when|where|why|which) (?P<Query1>.*) (?P<QuestionVerb>is|are|was|were) (?P<Query2>.*)"),
            re.compile(".*(?P<QuestionWord>who|what|when|where|why|which) (?P<QuestionVerb>\w+) (?P<Query>.*)")
        ]

    def _normalize(self, groupdict):
        if 'Query' in groupdict:
            return groupdict
        elif 'Query1' and 'Query2' in groupdict:
            return {
                'QuestionWord': groupdict.get('QuestionWord'),
                'QuestionVerb': groupdict.get('QuestionVerb'),
                'Query': ' '.join([groupdict.get('Query1'), groupdict.get('Query2')])
            }

    def parse(self, utterance):
        for regex in self.regexes:
            match = regex.match(utterance)
            if match:
                return self._normalize(match.groupdict())
        return None


class CerberusWolframAlphaClient(object):
    """
    Wolfram|Alpha v2.0 client
    """

    def query(self, query):
        """
        Query Wolfram|Alpha with query using the v2.0 API
        """
        identity = IdentityManager().get()
        bearer_token = 'Bearer %s:%s' % (identity.device_id, identity.token)
        query = urllib.parse.urlencode(dict(input=query))
        url = 'https://cerberus.mycroft.ai/wolframalpha/v2/query?' + query
        headers = {'Authorization': bearer_token}
        response = requests.get(url, headers=headers)
        if response.status_code == 401:
            raise CerberusAccessDenied()

        return wolframalpha.Result(StringIO(response.text))


class WolframAlphaSkill(MycroftSkill):
    def __init__(self):
        MycroftSkill.__init__(self, name="WolframAlphaSkill")
        self.__init_client()
        self.question_parser = EnglishQuestionParser()

    def __init_client(self):
        key = self.config.get('api_key')
        if key:
            self.client = wolframalpha.Client(key)
        else:
            self.client = CerberusWolframAlphaClient()

    def initialize(self):
        self.init_dialog(dirname(__file__))
        self.emitter.on('intent_failure', self.handle_fallback)

    def handle_fallback(self, message):
        logger.debug("Could not determine intent, falling back to WolframAlpha Skill!")
        utterance = message.metadata.get('utterance')
        parsed_question = self.question_parser.parse(utterance)

        # biding some time
        if parsed_question:
            self.speak("I am searching for " + parsed_question.get('Query'))
        else:
            self.speak("I am searching for " + utterance)
        query = utterance
        if parsed_question:<commit_msg>Issues 1 - Wolfram Alpha Skill Not Responding - Using decoded content from response<commit_after>from StringIO import StringIO
from os.path import dirname

import re
import requests
import wolframalpha
from six.moves import urllib

from mycroft.identity import IdentityManager
from mycroft.skills.core import MycroftSkill
from mycroft.util import CerberusAccessDenied
from mycroft.util.log import getLogger

__author__ = 'seanfitz'

logger = getLogger(__name__)


class EnglishQuestionParser(object):
    """
    Poor-man's english question parser. Not even close to conclusive, but appears to construct some decent w|a queries
    and responses.
    """

    def __init__(self):
        self.regexes = [
            re.compile(".*(?P<QuestionWord>who|what|when|where|why|which) (?P<Query1>.*) (?P<QuestionVerb>is|are|was|were) (?P<Query2>.*)"),
            re.compile(".*(?P<QuestionWord>who|what|when|where|why|which) (?P<QuestionVerb>\w+) (?P<Query>.*)")
        ]

    def _normalize(self, groupdict):
        if 'Query' in groupdict:
            return groupdict
        elif 'Query1' and 'Query2' in groupdict:
            return {
                'QuestionWord': groupdict.get('QuestionWord'),
                'QuestionVerb': groupdict.get('QuestionVerb'),
                'Query': ' '.join([groupdict.get('Query1'), groupdict.get('Query2')])
            }

    def parse(self, utterance):
        for regex in self.regexes:
            match = regex.match(utterance)
            if match:
                return self._normalize(match.groupdict())
        return None


class CerberusWolframAlphaClient(object):
    """
    Wolfram|Alpha v2.0 client
    """

    def query(self, query):
        """
        Query Wolfram|Alpha with query using the v2.0 API
        """
        identity = IdentityManager().get()
        bearer_token = 'Bearer %s:%s' % (identity.device_id, identity.token)
        query = urllib.parse.urlencode(dict(input=query))
        url = 'https://cerberus.mycroft.ai/wolframalpha/v2/query?' + query
        headers = {'Authorization': bearer_token}
        response = requests.get(url, headers=headers)
        if response.status_code == 401:
            raise CerberusAccessDenied()

        return wolframalpha.Result(StringIO(response.content))


class WolframAlphaSkill(MycroftSkill):
    def __init__(self):
        MycroftSkill.__init__(self, name="WolframAlphaSkill")
        self.__init_client()
        self.question_parser = EnglishQuestionParser()

    def __init_client(self):
        key = self.config.get('api_key')
        if key:
            self.client = wolframalpha.Client(key)
        else:
            self.client = CerberusWolframAlphaClient()

    def initialize(self):
        self.init_dialog(dirname(__file__))
        self.emitter.on('intent_failure', self.handle_fallback)

    def handle_fallback(self, message):
        logger.debug("Could not determine intent, falling back to WolframAlpha Skill!")
        utterance = message.metadata.get('utterance')
        parsed_question = self.question_parser.parse(utterance)

        # biding some time
        if parsed_question:
            self.speak("I am searching for " + parsed_question.get('Query'))
        else:
            self.speak("I am searching for " + utterance)
        query = utterance
        if parsed_question:
{'fraction_non_alphanumeric': 0.11183512653432338, 'fraction_numerical': 0.004394605243218669, 'mean_word_length': 2.793103448275862, 'pattern_counts': {'":': 0, '<': 17, '<?xml version=': 0, '>': 17, 'https://': 2, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '1676483', 'n_tokens_mistral': 2002, 'n_tokens_neox': 1926, 'n_words': 428}