From 0454d945c18c9ab0fe3ae530131b80d9a02560f0 Mon Sep 17 00:00:00 2001 From: kalzu Date: Thu, 29 Dec 2022 17:59:25 +0200 Subject: [PATCH] Kraken-fetch.py now has functioning auth system and added RSA key stuff for servers public/private setup, to be used to encrypt the responses. Made the demo-client.py work with current state of kraken-fetch.py. --- btc_tracker/kraken_fetch.py | 43 +++++++++++++++-------- demo-client.py | 69 ++++++++++++++++++------------------- 2 files changed, 63 insertions(+), 49 deletions(-) diff --git a/btc_tracker/kraken_fetch.py b/btc_tracker/kraken_fetch.py index 213e52b..d544bba 100755 --- a/btc_tracker/kraken_fetch.py +++ b/btc_tracker/kraken_fetch.py @@ -1,11 +1,11 @@ #!/usr/bin/python3 import krakenex, math -import json, sqlite3, binascii +import json, sqlite3, rsa import requests, os, time import threading, ecdsa from hashlib import sha256 -from flask import Flask, request +from flask import Flask, jsonify, request database = "btc_ohlc.db" app = Flask(__name__) @@ -15,6 +15,11 @@ user_publickeys = { "kalzu": 'f1debc13fb21fe0eee54525aa4f8aae5733b201c755edaa55f8893c90aa375b261a62eaa3110651ac5d7705d402581256a37508b0a1ca28bd919ea44710d9c88' } +## Generate the RSA keys for this instance +print("Generating RSA keys for this instance... just wait a bit...") +(server_public_key, server_private_key) = rsa.newkeys(4096) +server_public_key_string = server_public_key.save_pkcs1().decode('utf-8') + database_lock = threading.Lock() # Empty response json @@ -232,21 +237,20 @@ def get_the_data(): time.sleep(290) def check_auth(text, signature): - print(text) - print(signature) + ## Make bytes-object from given signature sig_bytes = bytes.fromhex(signature) - access_granted = 0 ## We will iterate over all user keys to determ who is we are talking to and should they have access for key, value in user_publickeys.items(): - ## What f*ck even is this? - vk = ecdsa.VerifyingKey.from_string(sig_bytes.fromhex(value), curve=ecdsa.SECP256k1) - if vk.verify(sig_bytes, text): + ## Create bytes-object from the public in 'value' variable + ## and use it to create VerifyingKey (vk) + public_key_bytes = bytes.fromhex(value) + vk = ecdsa.VerifyingKey.from_string(public_key_bytes, curve=ecdsa.SECP256k1) + try: + vk.verify(sig_bytes, bytes(text, 'utf-8')) print('user is', key) - access_granted = 1 - if access_granted != 0: - return True - else: - return False + return True + except ecdsa.BadSignatureError: + return False @app.route('/') def get_data(): @@ -259,7 +263,7 @@ def get_data(): signature = request.headers.get('auth') get_url = request.url if not check_auth(get_url, signature): - return 'Error with Authentication', 403 + return 'Access denied! Check your keys, maybe.', 403 database_lock.acquire() db = sqlite3.connect(database) @@ -288,6 +292,17 @@ def get_data(): return response, 200, {'Content-Type': 'application/json'} +@app.route('/serverkey') +def give_serverkey(): + + ## This endpoint also under Authentication? + signature = request.headers.get('auth') + get_url = request.url + if not check_auth(get_url, signature): + return 'Access denied! Check your keys, maybe.', 403 + + return jsonify({'public_key': server_public_key_string}) + if __name__ == '__main__': # Make sanity checks for the database Checkthedatabase() diff --git a/demo-client.py b/demo-client.py index ea7c6f8..fab0951 100755 --- a/demo-client.py +++ b/demo-client.py @@ -4,57 +4,56 @@ import requests from hashlib import sha256 import ecdsa -private_key = '03486537091ceb021fb313e5cf3eb04d44ca2f19f72112a1' -# we need to send server: -# the question: domain.tld/get/ -# the checksum: ?sum=sha256 -# the signed data: header 'auth' - -id = 123 -url = 'localhost:5000/get/' -url_id = url + str(id) -sum = sha256(url_id.encode('ascii')).hexdigest() -reg_url = 'http://' + url_id + '?sum=' + sum - -unsigned_data = url_id + '?' + 'sum=' + sum +#private_key = '03486537091ceb021fb313e5cf3eb04d44ca2f19f72112a1' +private_key = '039e1c137aa296d7af0cd55b468018ad1020949c2731e5141d032b8371490f48' # Generate SK from the private key private_key_int = int(private_key, 16) sk = ecdsa.SigningKey.from_secret_exponent(private_key_int, curve=ecdsa.SECP256k1) +## Get the server public key +url = 'http://localhost:5000/serverkey' + # sign the message -signature = sk.sign(unsigned_data.encode('utf-8')) +signature = sk.sign(url.encode('utf-8')) signature_hex = signature.hex() -print('we signed: ', unsigned_data) -print('We will send:') -print('to: ', reg_url) -print('sum: ', sum) -print('auth: ', signature_hex) -print('------------------------') - -response = requests.get(reg_url, headers={"auth":signature_hex}) +response = requests.get(url, headers={"auth":signature_hex}) print('>>> ', response.status_code) print('>>> ', response.content) -#ecdsa_public_key = '8716c78c09a4e4571a3112eca1c7ddce41289e20da446894b621f2a11ba91bc963f2e9fb9ddd5552c26faf814bc582b4' -ecdsa_public_key = '068716c78c09a4e4571a3112eca1c7ddce41289e20da446894b621f2a11ba91bc963f2e9fb9ddd5552c26faf814bc582b4' - -bytes_public_key = bytes.fromhex(ecdsa_public_key) - -bytes_signed_data = signature_hex.encode('utf-8') -vk = ecdsa.VerifyingKey.from_string(bytes_public_key, curve=ecdsa.SECP256k1) - -if vk.verify(signature_hex, unsigned_data): - response = "YES" -else: - response = "NO" - +## Get some kline data from the server +url = 'http://localhost:5000/?t=1672259440' +# sign the message +signature = sk.sign(url.encode('utf-8')) +signature_hex = signature.hex() +print('we signed: ', url) +print('We will send:') +print('to: ', url) +print('auth: ', signature_hex) +print('------------------------') +response = requests.get(url, headers={"auth":signature_hex}) +print('>>> ', response.status_code) +print('>>> ', response.content) +## +##bytes_public_key = bytes.fromhex(ecdsa_public_key) +## +##bytes_signed_data = signature_hex.encode('utf-8') +## +## +##vk = ecdsa.VerifyingKey.from_string(bytes_public_key, curve=ecdsa.SECP256k1) +## +##if vk.verify(signature_hex, unsigned_data): +## response = "YES" +##else: +## response = "NO" +## +## exit(0)