SatSale

Unnamed repository; edit this file 'description' to name the repository.
Log | Files | Refs | README | LICENSE

commit de9ab603175a3756556124702506da6a2da4c63e
parent 0831f51895d7291a4614e53c119b5dc80adb1c63
Author: Nick <nicholas.w.farrow@gmail.com>
Date:   Fri, 12 Nov 2021 17:35:43 +1100

Add Weakhands Mode (#23)

* Add new config option

* Require spending rights

* Better config explanation

* Send with max fee arg
Diffstat:
Mconfig.py | 7++++++-
Mnode/lnd.py | 8++++++++
Apayments/weakhands.py | 72++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Msatsale.py | 6++++--
4 files changed, 90 insertions(+), 3 deletions(-)

diff --git a/config.py b/config.py @@ -71,7 +71,7 @@ pay_method = "bitcoind" #lnd_macaroon = "invoice.macaroon" #lnd_cert = "tls.cert" -# Or clightning +# Or clightning #pay_method = "clightning" # If remote clightning, make sure `ssh -nNT -L lightning-rpc:{clightning_rpc_file} {tunnel_host}` @@ -83,6 +83,11 @@ pay_method = "bitcoind" lightning_address = None lightning_address_comment = None # Defaults to: "Thank you for your support <3" +# Weak Hands Mode - Automatically swap LN-BTC -> L-USDT using sideshift.ai +# https://blockstream.com/liquid/ +# Change lnd_macaroon='admin.macaroon', as you will also need to be able to spend with your lnd certificates. +# This is NOT a trustless swap. Exchange is carried out using sideshift.ai, you bear all associated exchange risks. +liquid_address = None # DO NOT CHANGE THIS TO TRUE UNLESS YOU WANT ALL PAYMENTS TO AUTOMATICALLY # BE CONSIDERED AS PAID. diff --git a/node/lnd.py b/node/lnd.py @@ -123,6 +123,14 @@ class lnd: address, r_hash = self.create_lnd_invoice(amount, memo=label) return address, r_hash + def pay_invoice(self, invoice): + ret = json.loads( + MessageToJson(self.lnd.send_payment(invoice, fee_limit_msat=20*1000)) + ) + print(ret) + return + + # Check whether the payment has been paid def check_payment(self, rhash): invoice_status = json.loads( diff --git a/payments/weakhands.py b/payments/weakhands.py @@ -0,0 +1,72 @@ +import requests + +import config + +# import config + +quote_url = "https://sideshift.ai/api/v1/quotes" +swap_url = "https://sideshift.ai/api/v1/orders" +affiliate = "eK590V1Mh" + +def get_quote(amount_lnbtc): + quote_data = { + "depositMethod": "ln", + "settleMethod": "usdtla", + "affiliateId": affiliate, + "depositAmount": str(amount_lnbtc) + } + print("Getting quote to swap {:.8f} LN-BTC to USDT".format(amount_lnbtc)) + resp = requests.post(quote_url, json=quote_data) + + if resp.status_code != 201: + print("Failed quote request:") + print(resp.json()) + return False + + return resp.json() + + +def get_swap(quote, amount_lnbtc, liquid_address): + swap_url = "https://sideshift.ai/api/orders" + data = { + "type": "fixed", + "quoteId": quote['id'], + "settleAddress": liquid_address, + "affiliateId": affiliate, + } + print("Creating order to swap {:.8f} LN-BTC to USDT (liquid: {})".format(amount_lnbtc, liquid_address)) + + resp = requests.post(swap_url, json=data) + + if resp.status_code != 201: + print("Failed to create order:") + print(resp.json()) + return False + + return resp.json() + +def pay_swap(node, swap): + payment_req = swap['depositAddress']['paymentRequest'] + print("Paying invoice: {}".format(payment_req)) + node.pay_invoice(payment_req) + return True + +def swap_lnbtc_for_lusdt(node, amount_lnbtc, liquid_address): + try: + quote = get_quote(amount_lnbtc) + if not quote: + print("Quote failed, not swapping this order.") + return False + + swap = get_swap(quote, amount_lnbtc, liquid_address) + if not swap: + print("Creating order failed, not swapping this payment.") + return False + + pay_swap(node, swap) + print("Paid invoice! Swapped ") + + except Exception as e: + print("Error encountered during swap: {}".format(e)) + + return diff --git a/satsale.py b/satsale.py @@ -17,7 +17,7 @@ import json from gateways import ssh_tunnel import config -from payments import database +from payments import database, weakhands from payments.price_feed import get_btc_value from node import bitcoind from node import lnd @@ -213,6 +213,9 @@ class complete_payment(Resource): if status["payment_complete"] != 1: return {"message": "You havent paid you stingy bastard"} + if (config.liquid_address is not None) and (invoice['method'] in ["lnd", "clightning"]): + weakhands.swap_lnbtc_for_lusdt(lightning_node, invoice["btc_value"], config.liquid_address) + # Call webhook to confirm payment with merchant if (invoice["webhook"] != None) and (invoice["webhook"] != ""): print("Calling webhook {}".format(invoice["webhook"])) @@ -313,6 +316,5 @@ if config.lightning_address is not None: from gateways import lightning_address lightning_address.add_ln_address_decorators(app, api, lightning_node) - if __name__ == "__main__": app.run(debug=False)