Module tronpytool.providers.http
tronpytool.providers.http
Class for configuring http providers
:copyright: © 2018 by the iEXBase. :license: MIT License
Expand source code
#!/usr/bin/env python
#
# --------------------------------------------------------------------
# Copyright (c) iEXBase. All rights reserved.
# Licensed under the MIT License.
# See License.txt in the project root for license information.
# --------------------------------------------------------------------
"""
tronpytool.providers.http
======================
Class for configuring http providers
:copyright: © 2018 by the iEXBase.
:license: MIT License
"""
import logging
from collections import namedtuple
from urllib.parse import urlparse
from eth_utils import to_dict
from requests import Session
from requests.exceptions import (
ConnectionError as TrxConnectionError
)
from tronpytool.common.encoding import to_text
from tronpytool.exceptions import HTTP_EXCEPTIONS, TransportError
from tronpytool.providers.base import BaseProvider
HTTP_SCHEMES = {'http', 'https'}
HttpResponse = namedtuple('HttpResponse', ('status_code', 'headers', 'data'))
log = logging.getLogger(__name__)
def is_valid_provider(provider) -> bool:
"""Check connected provider
Args:
provider(HttpProvider): Provider
"""
return isinstance(provider, HttpProvider)
class HttpProvider(BaseProvider):
"""A Connection object to make HTTP requests to a particular node."""
def __init__(self, node_url, request_kwargs=None):
"""Initializes a :class:`~tronpytool.providers.http.HttpProvider`
instance.
Args:
node_url (str): Url of the node to connect to.
request_kwargs (dict): Optional params to send with each request.
"""
self.node_url = node_url.rstrip('/')
uri = urlparse(node_url)
# This condition checks the node that will connect
# to work with methods.
if uri.scheme not in HTTP_SCHEMES:
raise NotImplementedError(
'TronAPI does not know how to connect to scheme %r in %r' % (
uri.scheme,
self.node_url,
)
)
self._request_kwargs = request_kwargs or {}
self.session = Session()
@to_dict
def get_request_kwargs(self):
"""Header settings"""
if 'headers' not in self._request_kwargs:
yield 'headers', self._http_default_headers()
for key, value in self._request_kwargs.items():
yield key, value
def request(self, path, json=None, params=None, method=None):
"""Performs an HTTP request with the given parameters.
Args:
path (str): API endpoint path (e.g.: ``'/transactions'``).
json (dict): JSON data to send along with the request.
params (dict): Dictionary of URL (query) parameters.
method (str): HTTP method (e.g.: ``'GET'``).
"""
try:
response = self._request(
method=method,
url=self.node_url + path if path else self.node_url,
json=json,
params=params,
**self.get_request_kwargs(),
)
except TrxConnectionError as err:
raise err
return response.data
def is_connected(self) -> bool:
"""Connection check
This method sends a test request to the connected node
to determine its health.
Returns:
bool: True if successful,
False otherwise.
"""
response = self.request(path=self.status_page, method='get')
if 'blockID' in response or response == 'OK':
return True
return False
def _request(self, **kwargs):
kwargs.setdefault('timeout', 60)
response = self.session.request(**kwargs)
text = response.text
try:
json = response.json()
except ValueError:
json = None
if not (200 <= response.status_code < 300):
exc_cls = HTTP_EXCEPTIONS.get(response.status_code, TransportError)
raise exc_cls(response.status_code, text, json, kwargs.get('url'))
data = json if json is not None else text
log.debug(data)
# Additional error interceptor that will occur in case of failed requests
if 'Error' in data:
raise ValueError(data['Error'])
self.__error_manager(data)
return HttpResponse(response.status_code, response.headers, data)
@staticmethod
def __error_manager(data):
"""Manager error
Args:
data (any): response data
"""
# Additional error interceptor that will occur in case of failed requests
if 'Error' in data:
raise ValueError(data['Error'])
# Convert hash errors
if 'code' in data and 'message' in data:
data['message'] = to_text(hexstr=data['message'])
Functions
def is_valid_provider(provider) ‑> bool
-
Check connected provider
Args
provider(HttpProvider): Provider
Expand source code
def is_valid_provider(provider) -> bool: """Check connected provider Args: provider(HttpProvider): Provider """ return isinstance(provider, HttpProvider)
Classes
class HttpProvider (node_url, request_kwargs=None)
-
A Connection object to make HTTP requests to a particular node.
Initializes a :class:
~tronpytool.providers.http.HttpProvider
instance.Args: node_url (str): Url of the node to connect to. request_kwargs (dict): Optional params to send with each request.
Expand source code
class HttpProvider(BaseProvider): """A Connection object to make HTTP requests to a particular node.""" def __init__(self, node_url, request_kwargs=None): """Initializes a :class:`~tronpytool.providers.http.HttpProvider` instance. Args: node_url (str): Url of the node to connect to. request_kwargs (dict): Optional params to send with each request. """ self.node_url = node_url.rstrip('/') uri = urlparse(node_url) # This condition checks the node that will connect # to work with methods. if uri.scheme not in HTTP_SCHEMES: raise NotImplementedError( 'TronAPI does not know how to connect to scheme %r in %r' % ( uri.scheme, self.node_url, ) ) self._request_kwargs = request_kwargs or {} self.session = Session() @to_dict def get_request_kwargs(self): """Header settings""" if 'headers' not in self._request_kwargs: yield 'headers', self._http_default_headers() for key, value in self._request_kwargs.items(): yield key, value def request(self, path, json=None, params=None, method=None): """Performs an HTTP request with the given parameters. Args: path (str): API endpoint path (e.g.: ``'/transactions'``). json (dict): JSON data to send along with the request. params (dict): Dictionary of URL (query) parameters. method (str): HTTP method (e.g.: ``'GET'``). """ try: response = self._request( method=method, url=self.node_url + path if path else self.node_url, json=json, params=params, **self.get_request_kwargs(), ) except TrxConnectionError as err: raise err return response.data def is_connected(self) -> bool: """Connection check This method sends a test request to the connected node to determine its health. Returns: bool: True if successful, False otherwise. """ response = self.request(path=self.status_page, method='get') if 'blockID' in response or response == 'OK': return True return False def _request(self, **kwargs): kwargs.setdefault('timeout', 60) response = self.session.request(**kwargs) text = response.text try: json = response.json() except ValueError: json = None if not (200 <= response.status_code < 300): exc_cls = HTTP_EXCEPTIONS.get(response.status_code, TransportError) raise exc_cls(response.status_code, text, json, kwargs.get('url')) data = json if json is not None else text log.debug(data) # Additional error interceptor that will occur in case of failed requests if 'Error' in data: raise ValueError(data['Error']) self.__error_manager(data) return HttpResponse(response.status_code, response.headers, data) @staticmethod def __error_manager(data): """Manager error Args: data (any): response data """ # Additional error interceptor that will occur in case of failed requests if 'Error' in data: raise ValueError(data['Error']) # Convert hash errors if 'code' in data and 'message' in data: data['message'] = to_text(hexstr=data['message'])
Ancestors
Methods
def get_request_kwargs(self)
-
Header settings
Expand source code
@to_dict def get_request_kwargs(self): """Header settings""" if 'headers' not in self._request_kwargs: yield 'headers', self._http_default_headers() for key, value in self._request_kwargs.items(): yield key, value
def is_connected(self) ‑> bool
-
Connection check
This method sends a test request to the connected node to determine its health.
Returns
bool
- True if successful,
False otherwise.
Expand source code
def is_connected(self) -> bool: """Connection check This method sends a test request to the connected node to determine its health. Returns: bool: True if successful, False otherwise. """ response = self.request(path=self.status_page, method='get') if 'blockID' in response or response == 'OK': return True return False
def request(self, path, json=None, params=None, method=None)
-
Performs an HTTP request with the given parameters.
Args
path
:str
- API endpoint path (e.g.:
'/transactions'
). json
:dict
- JSON data to send along with the request.
params
:dict
- Dictionary of URL (query) parameters.
method
:str
- HTTP method (e.g.:
'GET'
).
Expand source code
def request(self, path, json=None, params=None, method=None): """Performs an HTTP request with the given parameters. Args: path (str): API endpoint path (e.g.: ``'/transactions'``). json (dict): JSON data to send along with the request. params (dict): Dictionary of URL (query) parameters. method (str): HTTP method (e.g.: ``'GET'``). """ try: response = self._request( method=method, url=self.node_url + path if path else self.node_url, json=json, params=params, **self.get_request_kwargs(), ) except TrxConnectionError as err: raise err return response.data
Inherited members
class HttpResponse (status_code, headers, data)
-
HttpResponse(status_code, headers, data)
Ancestors
- builtins.tuple
Instance variables
var data
-
Alias for field number 2
var headers
-
Alias for field number 1
var status_code
-
Alias for field number 0