Skip to content
Snippets Groups Projects
Commit 2a9849f5 authored by Pascal Engélibert's avatar Pascal Engélibert :bicyclist:
Browse files

Change peer system

parent 60c57a6d
No related branches found
No related tags found
No related merge requests found
Pipeline #5707 passed
......@@ -5,6 +5,8 @@ run in an onion network, guaranteeing a strong anonymity.
## How to install it
**Warning**: This version works with a dev version of Silkaj. If the latest release of Silkaj is still `0.7.1`, please use [this branch](https://git.duniter.org/clients/python/silkaj/tree/223_endpoint_click_decoupled) (you can also copy `network_tools.py` from this branch).
### ➤ Debian (Ubuntu, Mint, etc.)
sh install_gmixer.sh
......
#!/usr/bin/env python3
"""
CopyLeft 2019 Pascal Engélibert <tuxmain@zettascript.org>
ĞMixer-py Test Client (only for testing server)
This file is part of ĞMixer-py.
......@@ -21,16 +22,13 @@ Sources:
https://www.ietf.org/rfc/rfc3092.txt <- Very important RFC, please read it
"""
import sys, os, asyncio, getpass, random, time, secrets
import sys, os, asyncio, getpass, random, time, secrets, socket
import ubjson
import plyvel
import libnacl.sign
from duniterpy.key import SigningKey, PublicKey
import utils
VERSION = "0.1.0"
AUTHORS = ["Pascal Engélibert <tuxmain@zettascript.org>"]
DIR = "~/.gmixer"
class Confirmation():
......@@ -66,26 +64,26 @@ class Confirmation():
}
def get_peers(host, proxy=None, proxy_onion_only=False):
header, content = utils.sdata(host, "GET", "/pubkey/list", proxy=proxy, proxy_onion_only=proxy_onion_only)
header, content = utils.sdata(host, "GET", "/peers/info", proxy=proxy, proxy_onion_only=proxy_onion_only)
try:
data = ubjson.loadb(content)
assert "pubkey" in data and "peers" in data
assert type(data["pubkey"]) == str and type(data["peers"]) == list
assert "info" in data and "peers" in data
assert type(data["peers"]) == list
except (ubjson.decoder.DecoderException, AssertionError):
print("Error: bad UBJSON")
return
peers = [utils.Peer(data["pubkey"], host[0], host[1], True)]
for peer in data["peers"]:
peers.append(utils.Peer(peer["pubkey"], peer["host"], peer["port"], peer["up"]))
peers = [utils.Peer(data["info"]), *[utils.Peer(p) for p in data["peers"]]]
#peers = [utils.Peer(p) for p in data["peers"]]
print([p.pubkey for p in peers])
return peers
def build_path(peers, receiver, layers=3):
up_peers = []
for peer in peers:
if peer.up:
#if peer.up:
up_peers.append(peer)
if len(up_peers) < layers:
return None, None
......@@ -99,11 +97,11 @@ def build_path(peers, receiver, layers=3):
break
path.append(peer.pubkey)
if host == None:
host = (peer.host, peer.port)
host = peer.host
path.append(receiver)
return host, path
def mix(db_txs, amount, base, sender, path, host, proxy=None, proxy_onion_only=False, send_tx=True):
async def mix(db_txs, amount, base, sender, path, host, proxy=None, proxy_onion_only=False, send_tx=True):
start_time = time.time()
onetime_keys = []
......@@ -254,14 +252,14 @@ def mix(db_txs, amount, base, sender, path, host, proxy=None, proxy_onion_only=F
if send_tx:
try:
utils.send_transaction(sender, path[0], amount, utils.gen_comment(comment_seeds[0]))
await utils.send_transaction(sender, path[0], amount, utils.gen_comment(comment_seeds[0]))
message["sent"] = True
db_txs.put(comment_seeds[0][1], PublicKey(sender.pubkey).encrypt_seal(ubjson.dumpb(message)))
except socket.timeout:
utils.logprint("Error when sending tx: timeout", LOG_ERROR)
print("Error when sending tx: timeout")
except Exception as e:
utils.logprint("Error when sending tx: " + str(e), LOG_ERROR)
print("Error when sending tx: " + str(e))
return
async def main(db_txs, host, receiver, amount=1000, layers=3, proxy=None, proxy_onion_only=False, send_tx=True):
......@@ -292,11 +290,11 @@ async def main(db_txs, host, receiver, amount=1000, layers=3, proxy=None, proxy_
if input("OK? [yn]: ").lower() == "y":
break
mix(db_txs, amount, 0, keys, path, host1, proxy, proxy_onion_only, send_tx)
await mix(db_txs, amount, 0, keys, path, host1, proxy, proxy_onion_only, send_tx)
if __name__ == "__main__":
if "--help" in sys.argv:
print("ĞMixer-py client "+VERSION+"""
print("ĞMixer-py client "+utils.VERSION+"""
Options:
-r <pubkey> receiver pubkey
......
This diff is collapsed.
#!/usr/bin/env python3
"""
CopyLeft 2019 Pascal Engélibert <tuxmain@zettascript.org>
This file is part of ĞMixer-py.
ĞMixer-py is free software: you can redistribute it and/or modify
......@@ -16,11 +17,15 @@
along with ĞMixer-py. If not, see <https://www.gnu.org/licenses/>.
"""
import sys, os, re, socket, time, secrets, hashlib
import sys, os, re, socket, time, secrets, hashlib, base64
import socks
import ubjson
import libnacl.sign
import plyvel
from duniterpy.key import SigningKey, PublicKey
import silkaj.money, silkaj.tx, silkaj.auth
import silkaj.money, silkaj.tx
VERSION = "0.2.0"
#-------- DATA
......@@ -37,7 +42,7 @@ def gen_keys() -> (str, str):
return secrets.token_urlsafe(), secrets.token_urlsafe()
def gen_comment(seeds:[bytes, bytes, bytes]) -> str:
return socks.b64encode(hashlib.sha512(b"".join(seeds)).digest()).decode()
return base64.urlsafe_b64encode(hashlib.sha512(b"".join(seeds)).digest()).decode()
#-------- NETWORK
......@@ -120,49 +125,62 @@ def getargv(arg:str, default:str="", n:int=1, args:list=sys.argv) -> str:
#-------- ĞMixer
class Peer:
def __init__(self, pubkey:str, host:str, port:int, up:bool):
self.pubkey = pubkey
self.host = host
self.port = int(port)
self.up = up
self.keys = PublicKey(pubkey)
def __str__(self) -> str:
return self.pubkey[:8] + "@" + self.host + ":" + str(self.port)
def export_str(self) -> str:
return self.pubkey + " " + self.host + " " + str(self.port)
# Read peers list
def read_peers(cdir:str) -> (list, dict):
if not os.path.isfile(cdir+"/peers"):
open(cdir+"/peers", "w").close()
peers = []
peers_index = {}
peersfile = open(cdir+"/peers", "r")
while True:
line = peersfile.readline()
if len(line) <= 1:
break
else:
cols = line.replace("\n", "").split(" ")
peer = Peer(cols[0], cols[1], cols[2], None)
peers.append(peer)
peers_index[peer.pubkey] = peer
peersfile.close()
return peers, peers_index
# Save peers list
def write_peers(cdir:str, peers:list):
peersfile = open(cdir+"/peers", "w")
VERSION = "1"
def __init__(self, raw:bytes):
self.rectime = time.time()
self.raw = raw
data = ubjson.loadb(raw)
pubkey = data["pubkey"]
raw = libnacl.sign.Verifier(PublicKey(pubkey).hex_pk()).verify(data["raw"])
data = ubjson.loadb(raw)
# TODO try except
# TODO tests
self.doctype = data["doctype"]
self.docver = data["docver"]
self.pubkey = data["pubkey"]
self.sigtime = data["sigtime"]
self.host = tuple(data["host"]) # socket cannot manage lists
self.idty = data["idty"]
self.idtysig = data["idtysig"]
self.hash = hashlib.sha512((self.pubkey+"@"+self.host[0]+":"+str(self.host[1])).encode()).digest()
self.keys = PublicKey(self.pubkey)
self.up = None
def to_human_str(self, short=True):
return (self.pubkey[:8] if short else self.pubkey)+"@"+self.host[0]+":"+str(self.host[1])
def generate(conf:dict, keys:SigningKey) -> bytes:
data = {
"doctype": "peer",
"docver": Peer.VERSION,
"pubkey": keys.pubkey,
"sigtime": time.time(),
"host": [conf["server"]["public_host"], conf["server"]["public_port"]],
"idty": conf["idty"]["pubkey"],
"idtysig": bytes.fromhex(conf["idty"]["sig"])
}
raw = keys.sign(ubjson.dumpb(data))
data = {
"pubkey": keys.pubkey,
"raw": raw
}
raw = ubjson.dumpb(data)
return Peer(raw)
def load_peers(db_peers:plyvel.DB, peers:dict):
for _, data in db_peers:
peer = Peer(data)
peers[peer.hash] = peer
def save_peers(db_peers:plyvel.DB, peers:dict):
for peer in peers:
peersfile.write(peer.export_str()+"\n")
peersfile.close()
db_peers.put(peers[peer].hash, peers[peer].raw)
def send_transaction(sender_keys:SigningKey, receiver_pubkey:str, amount:int, comment:str):
sender_amount = silkaj.money.get_amount_from_pubkey(sender_keys.pubkey)[0]
assert sender_amount >= amount, "not enough money"
async def send_transaction(sender_keys:SigningKey, receiver_pubkey:str, amount:int, comment:str):
#sender_amount = silkaj.money.get_amount_from_pubkey(sender_keys.pubkey)[0]
#assert sender_amount >= amount, "not enough money"
silkaj.tx.generate_and_send_transaction(sender_keys.hex_seed().decode(), sender_keys.pubkey, amount, [receiver_pubkey], comment)
await silkaj.tx.handle_intermediaries_transactions(sender_keys, sender_keys.pubkey, amount, [receiver_pubkey], comment)
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment