Example #1
0
class LexSession:
    LEX_URL = "https://runtime.lex.{}.amazonaws.com/bot/{}/alias/{}/user/{}/"

    def __init__(self,
                 bot,
                 alias,
                 user,
                 creds=None,
                 region='us-east-1',
                 profile=None):
        if not creds:
            self.creds = boto3.Session(profile_name=profile).get_credentials()
        # region can be changed to refer to boto3.Session().region_name
        self.region = region
        self.url = LexSession.LEX_URL.format(region, bot, alias, user)
        self.session = Session()

    def text(self, input_text, session_attributes=None):
        """input_text will be passed to your lex bot"""
        url = self.url + 'text'
        payload = json.dumps({
            "inputText": input_text,
            "sessionAttributes": session_attributes
        })
        request = AWSRequest(method="POST", url=url, data=payload)
        SigV4Auth(self.creds, 'lex', self.region).add_auth(request)

        return self.session.send(request.prepare()).json()

    def content(self, data, ctype, accept, session_attributes=None):
        """This will post any content to your lex bot

        Valid values for ctype and accept are found here:
        http://docs.aws.amazon.com/lex/latest/dg/API_PostContent.html"""
        url = self.url + 'content'
        request = AWSRequest(method="POST", url=url, data=data)
        request.headers["accept"] = accept
        request.headers["content-type"] = ctype
        if session_attributes:
            request.headers.add_header(
                "x-amz-lex-session-attributes",
                base64.b64encode(json.dumps(session_attributes)))
        LexContentSigV4Auth(self.creds, 'lex', self.region).add_auth(request)
        prepared = request.prepare()
        prepared.body = data

        return self.session.send(prepared)
    def send_to_es(self, path, method="GET", payload={}):
        """Low-level POST data to Amazon Elasticsearch Service generating a Sigv4 signed request

        Args:
            path (str): path to send to ES
            method (str, optional): HTTP method default:GET
            payload (dict, optional): additional payload used during POST or PUT

        Returns:
            dict: json answer converted in dict

        Raises:
            #: Error during ES communication
            ES_Exception: Description
        """
        if not path.startswith("/"):
            path = "/" + path

        es_region = self.cfg["es_endpoint"].split(".")[1]

        headers = {
                "Host": self.cfg["es_endpoint"],
                "Content-Type": "application/json"
            }

        # send to ES with exponential backoff
        retries = 0
        while retries < int(self.cfg["es_max_retry"]):
            if retries > 0:
                seconds = (2**retries) * .1
                time.sleep(seconds)

            req = AWSRequest(
                method=method,
                url="https://{}{}".format(
                    self.cfg["es_endpoint"], quote(path)),
                data=json.dumps(payload),
                params={"format": "json"},
                headers=headers)
            credential_resolver = create_credential_resolver(get_session())
            credentials = credential_resolver.load_credentials()
            SigV4Auth(credentials, 'es', es_region).add_auth(req)

            try:
                preq = req.prepare()
                session = Session()
                res = session.send(preq)
                if res.status_code >= 200 and res.status_code <= 299:
                    return json.loads(res.content)
                else:
                    raise ES_Exception(res.status_code, res._content)

            except ES_Exception as e:
                if (e.status_code >= 500) and (e.status_code <= 599):
                    retries += 1  # Candidate for retry
                else:
                    raise  # Stop retrying, re-raise exception
Example #3
0
    def send_to_es(self, path, method="GET", payload={}):
        """Low-level POST data to Amazon Elasticsearch Service generating a Sigv4 signed request

        Args:
            path (str): path to send to ES
            method (str, optional): HTTP method default:GET
            payload (dict, optional): additional payload used during POST or PUT

        Returns:
            dict: json answer converted in dict

        Raises:
            #: Error during ES communication
            ESException: Description
        """
        if not path.startswith("/"):
            path = "/" + path

        es_region = self.cfg["es_endpoint"].split(".")[1]

        req = AWSRequest(method=method,
                         url="https://%s%s?pretty&format=json" %
                         (self.cfg["es_endpoint"], quote(path)),
                         data=payload,
                         headers={'Host': self.cfg["es_endpoint"]})
        credential_resolver = create_credential_resolver(get_session())
        credentials = credential_resolver.load_credentials()
        SigV4Auth(credentials, 'es', es_region).add_auth(req)

        preq = req.prepare()
        session = Session()
        res = session.send(preq)
        session.close()
        if res.status_code >= 200 and res.status_code <= 299:
            return json.loads(res.content)
        else:
            raise ESException(res.status_code, res._content)
Example #4
0
    def send_to_es(self,
                   path="/",
                   method=None,
                   payload=None,
                   extra_headers=None):
        """Low-level POST data to Amazon Elasticsearch Service generating a Sigv4 signed request

        Args:
            path (str): path to send to ES
            method (str, optional): HTTP method default:GET
            payload (dict, optional): additional payload used during POST or PUT

        Returns:
            dict: json answer converted in dict

        Raises:
            #: Error during ES communication
            ESException: Description
        """
        # resolve default kwargs
        payload = payload or {}
        extra_headers = extra_headers or {}
        if not path.startswith("/"):
            path = "/" + path
        method = method if method else self.method
        es_region = self.cfg["es_endpoint"].split(".")[1]

        # send to ES with exponential backoff
        retries = 0
        while retries < int(self.cfg["es_max_retry"]):
            if retries > 0:
                seconds = (2**retries) * .1
                # print('Waiting for %.1f seconds', seconds)
                time.sleep(seconds)

            extra_headers.update({"Host": self.cfg["es_endpoint"]})
            req = AWSRequest(
                method=method,
                url=('https://%s%s?pretty&format=json' %
                     (self.cfg['es_endpoint'], urllib.parse.quote(path))),
                data=payload,
                headers=extra_headers)
            credential_resolver = create_credential_resolver(get_session())
            credentials = credential_resolver.load_credentials()
            SigV4Auth(credentials, 'es', es_region).add_auth(req)

            try:
                preq = req.prepare()
                session = Session()
                res = session.send(preq)
                if res.status_code >= 200 and res.status_code <= 299:
                    LOGGER.debug("%s %s", res.status_code, res.content)
                    return json.loads(res.content)
                else:
                    LOGGER.debug("%s %s", res.status_code, res.content)
                    raise ESException(res.status_code, res.content)

            except ESException as err:
                if (err.status_code >= 500) and (err.status_code <= 599):
                    retries += 1  # Candidate for retry
                else:
                    raise  # Stop retrying, re-raise exception