Adding API server files
This commit is contained in:
parent
937a12cc50
commit
1e2e688453
12
src/api/.gitignore
vendored
Normal file
12
src/api/.gitignore
vendored
Normal file
@ -0,0 +1,12 @@
|
||||
.vscode/
|
||||
__pycache__/
|
||||
*.swp
|
||||
config.py
|
||||
.idea/
|
||||
py3.7/
|
||||
py3/
|
||||
py3.8/
|
||||
*.db
|
||||
*.code-workspace
|
||||
*.log
|
||||
py*/
|
||||
1068
src/api/README.md
Normal file
1068
src/api/README.md
Normal file
File diff suppressed because it is too large
Load Diff
8
src/api/config-example.py
Normal file
8
src/api/config-example.py
Normal file
@ -0,0 +1,8 @@
|
||||
dbfolder = ''
|
||||
debug_status = False
|
||||
sse_pubKey = '<public key in the format of pybtc python library>'
|
||||
apiUrl = 'https://flosight.duckdns.org/api/'
|
||||
|
||||
# your apilayer.net access key
|
||||
apilayerAccesskey = '<accesskey>'
|
||||
|
||||
150
src/api/fetchRates.py
Normal file
150
src/api/fetchRates.py
Normal file
@ -0,0 +1,150 @@
|
||||
import requests
|
||||
import json
|
||||
import sqlite3
|
||||
import os
|
||||
from config import *
|
||||
import requests
|
||||
import json
|
||||
import sqlite3
|
||||
import os
|
||||
from config import *
|
||||
import time
|
||||
|
||||
RETRY_TIMEOUT_DB = 60 # 60 sec
|
||||
RETRY_TIMEOUT_REQUEST = 10 * 60 # 10 minsd
|
||||
|
||||
prices = {}
|
||||
# 1. fetch old price data if its there, else create an empty db
|
||||
def connect_database():
|
||||
if not os.path.isfile(f"system.db"):
|
||||
# create an empty db
|
||||
while True:
|
||||
try:
|
||||
conn = sqlite3.connect('system.db')
|
||||
c = conn.cursor()
|
||||
c.execute('''CREATE TABLE ratepairs
|
||||
(id integer primary key, ratepair text, price real)''')
|
||||
c.execute("INSERT INTO ratepairs(ratepair, price) VALUES ('BTCBTC', 1)")
|
||||
c.execute("INSERT INTO ratepairs(ratepair, price) VALUES ('BTCUSD', -1)")
|
||||
c.execute("INSERT INTO ratepairs(ratepair, price) VALUES ('BTCINR', -1)")
|
||||
c.execute("INSERT INTO ratepairs(ratepair, price) VALUES ('USDINR', -1)")
|
||||
c.execute("INSERT INTO ratepairs(ratepair, price) VALUES ('FLOUSD', -1)")
|
||||
conn.commit()
|
||||
conn.close()
|
||||
except:
|
||||
print(f"Unable to create system.db, retrying in {RETRY_TIMEOUT_DB} sec")
|
||||
time.sleep(RETRY_TIMEOUT_DB)
|
||||
else:
|
||||
break
|
||||
|
||||
|
||||
# load old price data
|
||||
# load older price data
|
||||
global prices
|
||||
while True:
|
||||
try:
|
||||
conn = sqlite3.connect('system.db')
|
||||
c = conn.cursor()
|
||||
ratepairs = c.execute('select ratepair, price from ratepairs')
|
||||
ratepairs = ratepairs.fetchall()
|
||||
for ratepair in ratepairs:
|
||||
ratepair = list(ratepair)
|
||||
prices[ratepair[0]] = ratepair[1]
|
||||
except:
|
||||
print(f"Unable to read system.db, retrying in {RETRY_TIMEOUT_DB} sec")
|
||||
time.sleep(RETRY_TIMEOUT_DB)
|
||||
else:
|
||||
break
|
||||
|
||||
# 2. fetch new price data
|
||||
def fetch_newprice():
|
||||
global prices
|
||||
while True:
|
||||
try:
|
||||
# apilayer
|
||||
response = requests.get(f"http://apilayer.net/api/live?access_key={apilayerAccesskey}")
|
||||
try:
|
||||
price = response.json()
|
||||
prices['USDINR'] = price['quotes']['USDINR']
|
||||
break
|
||||
except ValueError:
|
||||
print('Json parse error. retrying in {RETRY_TIMEOUT_REQUEST} sec')
|
||||
time.sleep(RETRY_TIMEOUT_REQUEST)
|
||||
except:
|
||||
print(f"Unable to fetch new price data, retrying in {RETRY_TIMEOUT_REQUEST} sec")
|
||||
time.sleep(RETRY_TIMEOUT_REQUEST)
|
||||
|
||||
|
||||
def fetch_bitpay_or_coindesk():
|
||||
# bitpay
|
||||
global prices
|
||||
while True:
|
||||
print("Trying bitpay API")
|
||||
try:
|
||||
response = requests.get('https://bitpay.com/api/rates')
|
||||
bitcoinRates = response.json()
|
||||
for currency in bitcoinRates:
|
||||
if currency['code'] == 'USD':
|
||||
prices['BTCUSD'] = currency['rate']
|
||||
elif currency['code'] == 'INR':
|
||||
prices['BTCINR'] = currency['rate']
|
||||
except ValueError:
|
||||
print("Json parse error in bitpay")
|
||||
except:
|
||||
print(f"Unable to fetch bitpay")
|
||||
else:
|
||||
break # if data is accrued from bitpay, break from loop and procees to next process
|
||||
print("Trying coindesk API")
|
||||
# coindesk
|
||||
try:
|
||||
response = requests.get('https://api.coindesk.com/v1/bpi/currentprice.json')
|
||||
price = response.json()
|
||||
prices['BTCUSD'] = price['bpi']['USD']['rate']
|
||||
except ValueError:
|
||||
print(f'Json parse error in coindesk')
|
||||
except:
|
||||
print(f"Unable to fetch coindesk")
|
||||
else:
|
||||
break # if data is accrued from coindesk, break from loop and procees to next process
|
||||
|
||||
print(f"Retrying in {RETRY_TIMEOUT_REQUEST} sec")
|
||||
time.sleep(RETRY_TIMEOUT_REQUEST)
|
||||
|
||||
|
||||
# cryptocompare
|
||||
def fetch_cryptocompare():
|
||||
while True:
|
||||
try:
|
||||
response = requests.get('https://min-api.cryptocompare.com/data/histoday?fsym=FLO&tsym=USD&limit=1&aggregate=3&e=CCCAGG')
|
||||
price = response.json()
|
||||
prices['FLOUSD'] = price['Data'][-1]['close']
|
||||
except ValueError:
|
||||
print(f'Json parse error in cryptocompare, retrying in {RETRY_TIMEOUT_REQUEST} sec')
|
||||
except:
|
||||
print(f"Unable to fetch cryptocompare, retrying in {RETRY_TIMEOUT_REQUEST} sec")
|
||||
else:
|
||||
break # if data is accrued from coindesk, break from loop and procees to next process
|
||||
|
||||
# 3. update latest price data
|
||||
def update_latest_prices():
|
||||
while True:
|
||||
try:
|
||||
conn = sqlite3.connect('system.db')
|
||||
c = conn.cursor()
|
||||
for pair in list(prices.items()):
|
||||
pair = list(pair)
|
||||
c.execute(f"UPDATE ratepairs SET price={pair[1]} WHERE ratepair='{pair[0]}'")
|
||||
conn.commit()
|
||||
except:
|
||||
print(f"Unable to write to system.db, retrying in {RETRY_TIMEOUT_DB} sec")
|
||||
time.sleep(RETRY_TIMEOUT_DB)
|
||||
else:
|
||||
break
|
||||
|
||||
connect_database()
|
||||
fetch_newprice()
|
||||
fetch_bitpay_or_coindesk()
|
||||
fetch_cryptocompare()
|
||||
print('\n\n')
|
||||
print(prices)
|
||||
update_latest_prices()
|
||||
1240
src/api/parsing.py
Normal file
1240
src/api/parsing.py
Normal file
File diff suppressed because it is too large
Load Diff
2880
src/api/ranchimallflo_api.py
Normal file
2880
src/api/ranchimallflo_api.py
Normal file
File diff suppressed because it is too large
Load Diff
31
src/api/requirements.txt
Normal file
31
src/api/requirements.txt
Normal file
@ -0,0 +1,31 @@
|
||||
aiofiles
|
||||
APScheduler==3.9.1
|
||||
arrow==0.15.2
|
||||
blinker==1.4
|
||||
certifi==2019.9.11
|
||||
cffi
|
||||
chardet==3.0.4
|
||||
Click==7.0
|
||||
h11==0.9.0
|
||||
h2==3.1.1
|
||||
hpack==3.0.0
|
||||
Hypercorn==0.8.2
|
||||
hyperframe==5.2.0
|
||||
idna==2.8
|
||||
itsdangerous==1.1.0
|
||||
Jinja2==2.10.1
|
||||
MarkupSafe==1.1.1
|
||||
multidict==4.5.2
|
||||
priority==1.3.0
|
||||
pyflo-lib==2.0.9
|
||||
pycparser==2.19
|
||||
python-dateutil==2.8.0
|
||||
Quart==0.10.0
|
||||
Quart-CORS==0.2.0
|
||||
requests==2.22.0
|
||||
six==1.12.0
|
||||
sortedcontainers==2.1.0
|
||||
toml==0.10.0
|
||||
typing-extensions==3.7.4
|
||||
urllib3==1.25.3
|
||||
wsproto==0.15.0
|
||||
24
src/api/static/broadcast.js
Normal file
24
src/api/static/broadcast.js
Normal file
@ -0,0 +1,24 @@
|
||||
document.addEventListener('DOMContentLoaded', function() {
|
||||
var es = new EventSource('/sse');
|
||||
es.onmessage = function (event) {
|
||||
var messages_dom = document.getElementsByTagName('ul')[0];
|
||||
var message_dom = document.createElement('li');
|
||||
var content_dom = document.createTextNode('Received: ' + event.data);
|
||||
message_dom.appendChild(content_dom);
|
||||
messages_dom.appendChild(message_dom);
|
||||
};
|
||||
|
||||
document.getElementById('send').onclick = function() {
|
||||
fetch('/', {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
'Accept': 'application/json',
|
||||
'Content-Type': 'application/json'
|
||||
},
|
||||
body: JSON.stringify ({
|
||||
message: document.getElementsByName("message")[0].value,
|
||||
}),
|
||||
});
|
||||
document.getElementsByName("message")[0].value = "";
|
||||
};
|
||||
});
|
||||
12
src/api/templates/index.html
Normal file
12
src/api/templates/index.html
Normal file
@ -0,0 +1,12 @@
|
||||
<!doctype html>
|
||||
<html>
|
||||
<head>
|
||||
<title>SSSE example</title>
|
||||
</head>
|
||||
<body>
|
||||
<input name="message" type="text"></input>
|
||||
<button id="send">Send</button>
|
||||
<ul></ul>
|
||||
<script type="text/javascript" src="{{ url_for('static', filename='broadcast.js') }}"></script>
|
||||
</body>
|
||||
</html>
|
||||
4
src/api/wsgi.py
Normal file
4
src/api/wsgi.py
Normal file
@ -0,0 +1,4 @@
|
||||
from ranchimallflo_api import app
|
||||
|
||||
if __name__ == "__main__":
|
||||
app.run()
|
||||
Loading…
Reference in New Issue
Block a user