|
# Class for gsheet API requests |
|
|
|
# Core imports |
|
from collections import OrderedDict |
|
import httplib2 |
|
import os |
|
from pprint import pprint |
|
|
|
# Third party imports |
|
from apiclient import discovery |
|
from oauth2client import client |
|
from oauth2client import tools |
|
from oauth2client.file import Storage |
|
from bittrex.bittrex import Bittrex, API_V1_1, API_V2_0 |
|
|
|
try: |
|
import argparse |
|
flags = argparse.ArgumentParser(parents=[tools.argparser]).parse_args() |
|
except ImportError: |
|
flags = None |
|
|
|
class GsheetAPI(): |
|
|
|
# If modifying these scopes, delete your previously saved credentials |
|
# at ~/.credentials/sheets.googleapis.com-python-quickstart.json |
|
SCOPES = 'https://www.googleapis.com/auth/spreadsheets' |
|
CLIENT_SECRET_FILE = 'client_secret.json' |
|
APPLICATION_NAME = 'Google Sheets API Python Quickstart' |
|
|
|
def get_credentials(self): |
|
"""Gets valid user credentials from storage. |
|
|
|
If nothing has been stored, or if the stored credentials are invalid, |
|
the OAuth2 flow is completed to obtain the new credentials. |
|
|
|
Returns: |
|
Credentials, the obtained credential. |
|
""" |
|
home_dir = os.path.expanduser('~') |
|
credential_dir = os.path.join(home_dir, '.credentials') |
|
if not os.path.exists(credential_dir): |
|
os.makedirs(credential_dir) |
|
credential_path = os.path.join(credential_dir, |
|
'sheets.googleapis.com-python-quickstart.json') |
|
|
|
store = Storage(credential_path) |
|
credentials = store.get() |
|
if not credentials or credentials.invalid: |
|
flow = client.flow_from_clientsecrets(self.CLIENT_SECRET_FILE, self.SCOPES) |
|
flow.user_agent = self.APPLICATION_NAME |
|
if flags: |
|
credentials = tools.run_flow(flow, store, flags) |
|
else: # Needed only for compatibility with Python 2.6 |
|
credentials = tools.run(flow, store) |
|
print('Storing credentials to ' + credential_path) |
|
return credentials |
|
|
|
def get_service(self): |
|
''' |
|
Method for returning an instance of the gsheets service |
|
''' |
|
credentials = self.get_credentials() |
|
http = credentials.authorize(httplib2.Http()) |
|
discoveryUrl = ('https://sheets.googleapis.com/$discovery/rest?' |
|
'version=v4') |
|
service = discovery.build('sheets', 'v4', http=http, |
|
discoveryServiceUrl=discoveryUrl) |
|
return service |
|
|
|
def populate_sheet(self, spreadsheet_id, cell_range, values): |
|
''' |
|
Function used to populate a specified gsheet |
|
spreadsheet_id: str "ID string of gsheet" |
|
cell_range: str "<sheetname>!<start_cell>:<end_cell> EG Data!A2:J" |
|
values: list "List of lists contaning dataset values" |
|
''' |
|
service = self.get_service() |
|
|
|
data = [ |
|
{ |
|
'range': cell_range, |
|
'values': values |
|
}, |
|
] |
|
|
|
body = { |
|
'valueInputOption': 'USER_ENTERED', |
|
'data': data |
|
} |
|
|
|
result = service.spreadsheets().values().batchUpdate( |
|
spreadsheetId=spreadsheet_id, body=body).execute() |
|
|
|
def clear_sheet(self, spreadsheet_id, cell_range): |
|
''' |
|
Clear all sheet cells |
|
''' |
|
service = self.get_service() |
|
request = service.spreadsheets().values().clear(spreadsheetId=spreadsheet_id, range=cell_range, body={}) |
|
response = request.execute() |
|
|
|
def create_gsheet_dataset(self, data_set): |
|
''' |
|
Function for converting a list of dict items |
|
to a list of lists |
|
''' |
|
column_headers = [header for header in data_set[0].keys()] |
|
column_values = [list(value.values()) for value in data_set] |
|
column_values.insert(0, column_headers) |
|
return column_values |
|
|
|
def get_column_ref(self, data_set): |
|
''' |
|
Return column ref based on column count |
|
This is a hacky way to return the last column ref |
|
and only supports 26 columns |
|
#TODO, improve method |
|
''' |
|
pos = len(data_set[0])-1 |
|
alphabet=['A','B','C','D','E','F','G','H','I','J', |
|
'K','L','M','P','Q','R','S','T','U','V','W','X','Y','Z'] |
|
return alphabet[pos] |
|
|
|
def populate_market_summaries_sheet(self, data_set): |
|
''' |
|
Populate the markets gsheet from API |
|
''' |
|
spreadsheet_id = '1WnRoxyonI2ew9VurGU8n0RMdCNmaP5_pxNu2jOb0f0g' |
|
values = self.create_gsheet_dataset(data_set) |
|
row_ref = self.get_column_ref(values) |
|
cell_range = 'Data!A1:{}'.format(row_ref) |
|
self.clear_sheet(spreadsheet_id, cell_range) |
|
self.populate_sheet(spreadsheet_id, cell_range, values) |
|
|
|
|
|
class BittrexApi(): |
|
|
|
# Get keys from environmental variables |
|
# See https://12factor.net/ |
|
api_key = os.environ['BITTREX_API_KEY'] |
|
api_secret = os.environ['BITTREX_API_SECRET'] |
|
|
|
def init_bittrex_api(self, version): |
|
''' |
|
Instantiates the bitrex API based on version |
|
''' |
|
return Bittrex(self.api_key, self.api_secret, api_version=version) |
|
|
|
def get_market_summaries(self): |
|
''' |
|
Used to get the last 24 hour summary of all active exchanges |
|
Method support: API ver 1 & 2 |
|
''' |
|
my_bittrex = self.init_bittrex_api(version=API_V2_0) |
|
market_summaries = my_bittrex.get_market_summaries() |
|
market_summaries_result = market_summaries['result'] |
|
order_list = [] |
|
for summary in market_summaries_result: |
|
merged_dict = {**summary['Market'], **summary['Summary']} |
|
ordered_dict = OrderedDict(sorted(merged_dict.items())) |
|
order_list.append(ordered_dict) |
|
return order_list |
|
|
|
if __name__ == '__main__': |
|
|
|
# Instantiate classes |
|
bittrex_api = BittrexApi() |
|
gsheet_api = GsheetAPI() |
|
|
|
def populate_market_summaries_sheet(): |
|
market_summaries_list = bittrex_api.get_market_summaries() |
|
gsheet_api.populate_market_summaries_sheet(market_summaries_list) |
|
|
|
populate_market_summaries_sheet() |