fix exceptions related to btcpay HTTP calls. better cleanup of expired

btcpay invoices.
This commit is contained in:
forest 2020-07-18 10:16:17 -05:00
parent 2f60e2715e
commit e6021324f7
3 changed files with 32 additions and 5 deletions

View File

@ -1,6 +1,7 @@
import os import os
import re import re
import sys
from datetime import datetime, timedelta from datetime import datetime, timedelta
import click import click
@ -86,7 +87,16 @@ def clean_up_unresolved_btcpay_invoices():
unresolved_btcpay_invoices = get_model().get_unresolved_btcpay_invoices() unresolved_btcpay_invoices = get_model().get_unresolved_btcpay_invoices()
for unresolved_invoice in unresolved_btcpay_invoices: for unresolved_invoice in unresolved_btcpay_invoices:
invoice_id = unresolved_invoice['id'] invoice_id = unresolved_invoice['id']
btcpay_invoice = current_app.config['BTCPAY_CLIENT'].get_invoice(invoice_id) btcpay_invoice = None
try:
btcpay_invoice = current_app.config['BTCPAY_CLIENT'].get_invoice(invoice_id)
except:
current_app.logger.error(f"""
error was thrown when contacting btcpay server for invoice {invoice_id}:
{my_exec_info_message(sys.exc_info())}"""
)
continue
days = float((datetime.now() - unresolved_invoice['created']).total_seconds())/float(60*60*24) days = float((datetime.now() - unresolved_invoice['created']).total_seconds())/float(60*60*24)
if btcpay_invoice['status'] == "complete": if btcpay_invoice['status'] == "complete":
@ -102,6 +112,7 @@ def clean_up_unresolved_btcpay_invoices():
f"btcpay server invoice status: {btcpay_invoice['status']}" f"btcpay server invoice status: {btcpay_invoice['status']}"
) )
get_model().btcpay_invoice_resolved(invoice_id, False) get_model().btcpay_invoice_resolved(invoice_id, False)
get_model().delete_payment_session("btcpay", invoice_id)
delete_at_account_balance_dollars = -10 delete_at_account_balance_dollars = -10

View File

@ -218,6 +218,10 @@ class DBModel:
else: else:
return None return None
def delete_payment_session(self, payment_type, id):
self.cursor.execute( "DELETE FROM payment_sessions WHERE id = %s AND type = %s", (id, payment_type) )
self.connection.commit()
def btcpay_invoice_resolved(self, id, completed): def btcpay_invoice_resolved(self, id, completed):
self.cursor.execute("SELECT email, payment_id FROM unresolved_btcpay_invoices WHERE id = %s ", (id,)) self.cursor.execute("SELECT email, payment_id FROM unresolved_btcpay_invoices WHERE id = %s ", (id,))
row = self.cursor.fetchone() row = self.cursor.fetchone()

View File

@ -3,6 +3,7 @@ import json
import time import time
import decimal import decimal
import re import re
import sys
from time import sleep from time import sleep
from flask import Blueprint from flask import Blueprint
@ -19,7 +20,7 @@ from werkzeug.exceptions import abort
from capsulflask.auth import account_required from capsulflask.auth import account_required
from capsulflask.db import get_model from capsulflask.db import get_model, my_exec_info_message
bp = Blueprint("payment", __name__, url_prefix="/payment") bp = Blueprint("payment", __name__, url_prefix="/payment")
@ -80,15 +81,24 @@ def btcpay_payment():
def poll_btcpay_session(invoice_id): def poll_btcpay_session(invoice_id):
# so you better make sure to get the invoice directly from the horses mouth!
invoice = current_app.config['BTCPAY_CLIENT'].get_invoice(invoice_id) invoice = None
try:
invoice = current_app.config['BTCPAY_CLIENT'].get_invoice(invoice_id)
except:
current_app.logger.error(f"""
error was thrown when contacting btcpay server:
{my_exec_info_message(sys.exc_info())}"""
)
return [503, "error was thrown when contacting btcpay server"]
if invoice['currency'] != "USD": if invoice['currency'] != "USD":
return [400, "invalid currency"] return [400, "invalid currency"]
dollars = invoice['price'] dollars = invoice['price']
current_app.logger.info(f"got btcpay webhook with invoice_id={invoice_id}, status={invoice['status']} dollars={dollars}") current_app.logger.info(f"poll_btcpay_session invoice_id={invoice_id}, status={invoice['status']} dollars={dollars}")
if invoice['status'] == "paid" or invoice['status'] == "confirmed" or invoice['status'] == "complete": if invoice['status'] == "paid" or invoice['status'] == "confirmed" or invoice['status'] == "complete":
success_account = get_model().consume_payment_session("btcpay", invoice_id, dollars) success_account = get_model().consume_payment_session("btcpay", invoice_id, dollars)
@ -100,6 +110,7 @@ def poll_btcpay_session(invoice_id):
get_model().btcpay_invoice_resolved(invoice_id, True) get_model().btcpay_invoice_resolved(invoice_id, True)
elif invoice['status'] == "expired" or invoice['status'] == "invalid": elif invoice['status'] == "expired" or invoice['status'] == "invalid":
get_model().btcpay_invoice_resolved(invoice_id, False) get_model().btcpay_invoice_resolved(invoice_id, False)
get_model().delete_payment_session("btcpay", invoice_id)
return [200, "ok"] return [200, "ok"]
@ -113,6 +124,7 @@ def btcpay_webhook():
request_data = json.loads(request.data) request_data = json.loads(request.data)
invoice_id = request_data['id'] invoice_id = request_data['id']
# so you better make sure to get the invoice directly from the horses mouth!
result = poll_btcpay_session(invoice_id) result = poll_btcpay_session(invoice_id)
abort(result[0], result[1]) abort(result[0], result[1])