From 15a2392d44642af2f84b01e73988e18bbc5ab62a Mon Sep 17 00:00:00 2001 From: Marco Rosa Date: Mon, 11 Dec 2017 22:38:48 +0100 Subject: [PATCH 1/9] add gemini exchange --- exchanges/gemini.py | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) create mode 100644 exchanges/gemini.py diff --git a/exchanges/gemini.py b/exchanges/gemini.py new file mode 100644 index 0000000..0e23509 --- /dev/null +++ b/exchanges/gemini.py @@ -0,0 +1,18 @@ +from exchanges.base import Exchange + + +class Gemini(Exchange): + + TICKER_URL = 'https://api.gemini.com/v1/pubticker/btcusd' + + @classmethod + def _current_price_extractor(cls, data): + return data.get('last') + + @classmethod + def _current_bid_extractor(cls, data): + return data.get('bid') + + @classmethod + def _current_ask_extractor(cls, data): + return data.get('ask') From 788073b75ce47fa6bf60ce5653b5c1c8c8965cc0 Mon Sep 17 00:00:00 2001 From: Marco Rosa Date: Tue, 12 Dec 2017 00:07:37 +0100 Subject: [PATCH 2/9] add get_historical_data methods --- exchanges/gemini.py | 32 ++++++++++++++++++++++++++++++++ 1 file changed, 32 insertions(+) diff --git a/exchanges/gemini.py b/exchanges/gemini.py index 0e23509..fb3717a 100644 --- a/exchanges/gemini.py +++ b/exchanges/gemini.py @@ -1,4 +1,7 @@ +from datetime import datetime, timedelta +from decimal import Decimal from exchanges.base import Exchange +from helpers import get_response class Gemini(Exchange): @@ -16,3 +19,32 @@ def _current_bid_extractor(cls, data): @classmethod def _current_ask_extractor(cls, data): return data.get('ask') + + @classmethod + def get_historical_data_as_dict(cls, start='2013-09-01'): + start_date = datetime.strptime(start, '%Y-%m-%d') + delta = datetime.today() - start_date + days = [start_date + timedelta(x) for x in range(delta.days + 1)] + data = map(cls._get_historical_data, days) + prices = {datetime.strftime(k, '%Y-%m-%d'): Decimal(str(v['price'])) + for (k, v) in zip(days, data)} + return prices + + @classmethod + def get_historical_data_as_list(cls, start='2013-09-01'): + pass + start_date = datetime.strptime(start, '%Y-%m-%d') + delta = datetime.today() - start_date + days = [start_date + timedelta(x) for x in range(delta.days + 1)] + data = map(lambda day: cls._get_historical_data(day), days) + ret = [ + {datetime.strftime(k, '%Y-%m-%d'): Decimal(str(v['price']))} + for (k, v) in zip(days, data) + ] + return ret + + @classmethod + def _get_historical_data(cls, day): + url = 'https://api.gemini.com/v1/trades/btcusd?since=%s&limit_trades=1' + print(day) + return get_response(url % day.strftime('%s'))[0] From e5e01794d49e061a626306fd8510ed0705bf9dd4 Mon Sep 17 00:00:00 2001 From: Marco Rosa Date: Tue, 12 Dec 2017 00:11:26 +0100 Subject: [PATCH 3/9] make get_historical_data_as_list consistent with coindesk --- exchanges/gemini.py | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/exchanges/gemini.py b/exchanges/gemini.py index fb3717a..86d148d 100644 --- a/exchanges/gemini.py +++ b/exchanges/gemini.py @@ -27,7 +27,7 @@ def get_historical_data_as_dict(cls, start='2013-09-01'): days = [start_date + timedelta(x) for x in range(delta.days + 1)] data = map(cls._get_historical_data, days) prices = {datetime.strftime(k, '%Y-%m-%d'): Decimal(str(v['price'])) - for (k, v) in zip(days, data)} + for (k,v) in zip(days, data)} return prices @classmethod @@ -38,13 +38,13 @@ def get_historical_data_as_list(cls, start='2013-09-01'): days = [start_date + timedelta(x) for x in range(delta.days + 1)] data = map(lambda day: cls._get_historical_data(day), days) ret = [ - {datetime.strftime(k, '%Y-%m-%d'): Decimal(str(v['price']))} - for (k, v) in zip(days, data) + {'date': datetime.strftime(k, '%Y-%m-%d'), + 'price': Decimal(str(v['price']))} + for (k,v) in zip(days, data) ] return ret @classmethod def _get_historical_data(cls, day): url = 'https://api.gemini.com/v1/trades/btcusd?since=%s&limit_trades=1' - print(day) return get_response(url % day.strftime('%s'))[0] From c2eab5b34e42c897df3ec571e90a14390d5203df Mon Sep 17 00:00:00 2001 From: Marco Rosa Date: Tue, 12 Dec 2017 18:02:23 +0100 Subject: [PATCH 4/9] add coinbase exchange --- exchanges/coinbase.py | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) create mode 100644 exchanges/coinbase.py diff --git a/exchanges/coinbase.py b/exchanges/coinbase.py new file mode 100644 index 0000000..50837a9 --- /dev/null +++ b/exchanges/coinbase.py @@ -0,0 +1,24 @@ +from decimal import Decimal + +from exchanges.base import Exchange +from exchanges.helpers import get_response + + +class Coinbase(Exchange): + + TICKER_URL = 'https://api.coinbase.com/v2/prices/BTC-{}/{}' + + @classmethod + def get_current_price(cls, currency='USD'): + url = cls.TICKER_URL.format(currency, 'spot') + data = get_response(url) + price = data.get('data').get('amount') + return Decimal(price) + + @classmethod + def get_current_bid(cls): + return None + + @classmethod + def get_current_ask(cls): + return None From 3947cf6ab3b3f9bcefd7bc2ad5010e23b3b2ba57 Mon Sep 17 00:00:00 2001 From: Marco Rosa Date: Wed, 13 Dec 2017 12:31:23 +0100 Subject: [PATCH 5/9] add cex.io exchange --- exchanges/cex.py | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) create mode 100644 exchanges/cex.py diff --git a/exchanges/cex.py b/exchanges/cex.py new file mode 100644 index 0000000..662f3ed --- /dev/null +++ b/exchanges/cex.py @@ -0,0 +1,18 @@ +from exchanges.base import Exchange + + +class Cex(Exchange): + + TICKER_URL = 'https://cex.io/api/ticker/BTC/USD' + + @classmethod + def _current_price_extractor(cls, data): + return data.get('last') + + @classmethod + def _current_bid_extractor(cls, data): + return data.get('bid') + + @classmethod + def _current_ask_extractor(cls, data): + return data.get('ask') From b603efde087bd8aa0ebf585a7903e4d332ea9070 Mon Sep 17 00:00:00 2001 From: PokestarFan Date: Sat, 6 Jan 2018 15:52:39 -0500 Subject: [PATCH 6/9] Update setup.py Removed excess imports --- setup.py | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/setup.py b/setup.py index c01788b..359708b 100644 --- a/setup.py +++ b/setup.py @@ -1,11 +1,7 @@ # Copyright (C) 2015 Bitquant Research Laboratories (Asia) Limited # Released under the Simplified BSD License -from setuptools import ( - setup, - find_packages, -) - +from setuptools import setup setup( name='bitcoin-price-api', version = '0.0.4', From 9803937e3617960424e8ac09ca8d4110bac538bd Mon Sep 17 00:00:00 2001 From: PokestarFan Date: Sat, 6 Jan 2018 15:54:21 -0500 Subject: [PATCH 7/9] Add versions Otherwise latest will install --- setup.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/setup.py b/setup.py index 359708b..655ac35 100644 --- a/setup.py +++ b/setup.py @@ -12,6 +12,6 @@ long_description='''Price API's for bitcoin exchanges''', license='MIT', packages=['exchanges'], - install_requires = ['requests', 'python-dateutil'], + install_requires = ['python-dateutil==2.4.2', 'requests==2.9.1'], use_2to3 = True ) From a3af06f1cbe5deb30e99e8026e9dc27366df3100 Mon Sep 17 00:00:00 2001 From: Marco Rosa Date: Sun, 7 Jan 2018 21:50:39 +0100 Subject: [PATCH 8/9] increment pypi version v0.0.4 offers broken Coindesk apis --- setup.py | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/setup.py b/setup.py index 655ac35..f311b9c 100644 --- a/setup.py +++ b/setup.py @@ -2,9 +2,11 @@ # Released under the Simplified BSD License from setuptools import setup + + setup( name='bitcoin-price-api', - version = '0.0.4', + version='0.0.5', author='Matthew Madurski', author_email='madurskimr@gmail.com', url='https://github.com/dursk/bitcoin-price-api', @@ -12,6 +14,6 @@ long_description='''Price API's for bitcoin exchanges''', license='MIT', packages=['exchanges'], - install_requires = ['python-dateutil==2.4.2', 'requests==2.9.1'], - use_2to3 = True + install_requires=['python-dateutil==2.4.2', 'requests==2.9.1'], + use_2to3=True ) From 3c6967ac16aa5210221251c6a594e89016e4615e Mon Sep 17 00:00:00 2001 From: Zihan Chen Date: Sat, 24 Feb 2018 17:28:19 -0800 Subject: [PATCH 9/9] Added bid/ask implementation --- exchanges/coinbase.py | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/exchanges/coinbase.py b/exchanges/coinbase.py index 50837a9..5184a50 100644 --- a/exchanges/coinbase.py +++ b/exchanges/coinbase.py @@ -9,16 +9,20 @@ class Coinbase(Exchange): TICKER_URL = 'https://api.coinbase.com/v2/prices/BTC-{}/{}' @classmethod - def get_current_price(cls, currency='USD'): - url = cls.TICKER_URL.format(currency, 'spot') + def _get_current_price(cls, currency='USD', price_type='spot'): + url = cls.TICKER_URL.format(currency, price_type) data = get_response(url) price = data.get('data').get('amount') return Decimal(price) @classmethod - def get_current_bid(cls): - return None + def get_current_price(cls, currency='USD'): + return cls._get_current_price(currency=currency, price_type='spot') + + @classmethod + def get_current_bid(cls, currency='USD'): + return cls._get_current_price(currency=currency, price_type='buy') @classmethod - def get_current_ask(cls): - return None + def get_current_ask(cls, currency='USD'): + return cls._get_current_price(currency=currency, price_type='sell')