changed polling to invoice listener

- fixed issue #213
This commit is contained in:
Tiago vasconcelos 2021-06-15 12:32:23 +01:00
parent 1e0367a451
commit 1667e60464
5 changed files with 111 additions and 64 deletions

View File

@ -10,3 +10,8 @@ lnticket_ext: Blueprint = Blueprint(
from .views_api import * # noqa from .views_api import * # noqa
from .views import * # noqa from .views import * # noqa
from .tasks import register_listeners
from lnbits.tasks import record_async
lnticket_ext.record(record_async(register_listeners))

View File

@ -0,0 +1,34 @@
import json
import trio # type: ignore
from lnbits.core.models import Payment
from lnbits.core.crud import create_payment
from lnbits.core import db as core_db
from lnbits.tasks import register_invoice_listener, internal_invoice_paid
from lnbits.helpers import urlsafe_short_hash
from .crud import get_ticket, set_ticket_paid
async def register_listeners():
invoice_paid_chan_send, invoice_paid_chan_recv = trio.open_memory_channel(2)
register_invoice_listener(invoice_paid_chan_send)
await wait_for_paid_invoices(invoice_paid_chan_recv)
async def wait_for_paid_invoices(invoice_paid_chan: trio.MemoryReceiveChannel):
async for payment in invoice_paid_chan:
await on_invoice_paid(payment)
async def on_invoice_paid(payment: Payment) -> None:
if "lnticket" != payment.extra.get("tag"):
# not a lnticket invoice
return
ticket = await get_ticket(payment.payment_hash)
if not ticket:
print("this should never happen", payment)
return
await payment.set_pending(False)
await set_ticket_paid(payment_hash=payment.payment_hash)

View File

@ -99,7 +99,11 @@
show: false, show: false,
status: 'pending', status: 'pending',
paymentReq: null paymentReq: null
} },
wallet: {
inkey: ''
},
cancelListener: () => {}
} }
}, },
computed: { computed: {
@ -128,12 +132,35 @@
}, },
closeReceiveDialog: function () { closeReceiveDialog: function () {
var checker = this.receive.paymentChecker var checker = this.startPaymentNotifier
dismissMsg() dismissMsg()
clearInterval(paymentChecker)
setTimeout(function () {}, 10000) setTimeout(function () {}, 10000)
}, },
startPaymentNotifier() {
this.cancelListener()
console.log(this.wallet)
this.cancelListener = LNbits.events.onInvoicePaid(
this.wallet,
payment => {
this.receive = {
show: false,
status: 'complete',
paymentReq: null
}
dismissMsg()
this.formDialog.data.name = ''
this.formDialog.data.email = ''
this.formDialog.data.text = ''
this.$q.notify({
type: 'positive',
message: 'Sent, thank you!',
icon: 'thumb_up'
})
}
)
},
Invoice: function () { Invoice: function () {
var self = this var self = this
axios axios
@ -158,39 +185,15 @@
status: 'pending', status: 'pending',
paymentReq: self.paymentReq paymentReq: self.paymentReq
} }
paymentChecker = setInterval(function () {
axios
.get('/lnticket/api/v1/tickets/' + self.paymentCheck)
.then(function (res) {
if (res.data.paid) {
clearInterval(paymentChecker)
self.receive = {
show: false,
status: 'complete',
paymentReq: null
}
dismissMsg()
self.formDialog.data.name = ''
self.formDialog.data.email = ''
self.formDialog.data.text = ''
self.$q.notify({
type: 'positive',
message: 'Sent, thank you!',
icon: 'thumb_up'
})
}
})
.catch(function (error) {
LNbits.utils.notifyApiError(error)
})
}, 2000)
}) })
.catch(function (error) { .catch(function (error) {
LNbits.utils.notifyApiError(error) LNbits.utils.notifyApiError(error)
}) })
} }
},
created() {
this.wallet.inkey = '{{form_wallet}}'
this.startPaymentNotifier()
} }
}) })
</script> </script>

View File

@ -230,7 +230,7 @@
</div> </div>
{% endblock %} {% block scripts %} {{ window_vars(user) }} {% endblock %} {% block scripts %} {{ window_vars(user) }}
<script> <script>
var mapLNTicket = function(obj) { var mapLNTicket = function (obj) {
obj.date = Quasar.utils.date.formatDate( obj.date = Quasar.utils.date.formatDate(
new Date(obj.time * 1000), new Date(obj.time * 1000),
'YYYY-MM-DD HH:mm' 'YYYY-MM-DD HH:mm'
@ -243,7 +243,7 @@
new Vue({ new Vue({
el: '#vue', el: '#vue',
mixins: [windowMixin], mixins: [windowMixin],
data: function() { data: function () {
return { return {
forms: [], forms: [],
tickets: [], tickets: [],
@ -294,7 +294,7 @@
} }
}, },
methods: { methods: {
getTickets: function() { getTickets: function () {
var self = this var self = this
LNbits.api LNbits.api
@ -303,40 +303,40 @@
'/lnticket/api/v1/tickets?all_wallets', '/lnticket/api/v1/tickets?all_wallets',
this.g.user.wallets[0].inkey this.g.user.wallets[0].inkey
) )
.then(function(response) { .then(function (response) {
self.tickets = response.data.map(function(obj) { self.tickets = response.data.map(function (obj) {
return mapLNTicket(obj) return mapLNTicket(obj)
}) })
}) })
}, },
deleteTicket: function(ticketId) { deleteTicket: function (ticketId) {
var self = this var self = this
var tickets = _.findWhere(this.tickets, {id: ticketId}) var tickets = _.findWhere(this.tickets, {id: ticketId})
LNbits.utils LNbits.utils
.confirmDialog('Are you sure you want to delete this ticket') .confirmDialog('Are you sure you want to delete this ticket')
.onOk(function() { .onOk(function () {
LNbits.api LNbits.api
.request( .request(
'DELETE', 'DELETE',
'/lnticket/api/v1/tickets/' + ticketId, '/lnticket/api/v1/tickets/' + ticketId,
_.findWhere(self.g.user.wallets, {id: tickets.wallet}).inkey _.findWhere(self.g.user.wallets, {id: tickets.wallet}).inkey
) )
.then(function(response) { .then(function (response) {
self.tickets = _.reject(self.tickets, function(obj) { self.tickets = _.reject(self.tickets, function (obj) {
return obj.id == ticketId return obj.id == ticketId
}) })
}) })
.catch(function(error) { .catch(function (error) {
LNbits.utils.notifyApiError(error) LNbits.utils.notifyApiError(error)
}) })
}) })
}, },
exportticketsCSV: function() { exportticketsCSV: function () {
LNbits.utils.exportCSV(this.ticketsTable.columns, this.tickets) LNbits.utils.exportCSV(this.ticketsTable.columns, this.tickets)
}, },
getForms: function() { getForms: function () {
var self = this var self = this
LNbits.api LNbits.api
@ -345,16 +345,17 @@
'/lnticket/api/v1/forms?all_wallets', '/lnticket/api/v1/forms?all_wallets',
this.g.user.wallets[0].inkey this.g.user.wallets[0].inkey
) )
.then(function(response) { .then(function (response) {
self.forms = response.data.map(function(obj) { self.forms = response.data.map(function (obj) {
return mapLNTicket(obj) return mapLNTicket(obj)
}) })
}) })
}, },
sendFormData: function() { sendFormData: function () {
var wallet = _.findWhere(this.g.user.wallets, { var wallet = _.findWhere(this.g.user.wallets, {
id: this.formDialog.data.wallet id: this.formDialog.data.wallet
}) })
this.formDialog.data.inkey = wallet.inkey
var data = this.formDialog.data var data = this.formDialog.data
if (data.id) { if (data.id) {
@ -364,22 +365,23 @@
} }
}, },
createForm: function(wallet, data) { createForm: function (wallet, data) {
var self = this var self = this
console.log('create', data)
LNbits.api LNbits.api
.request('POST', '/lnticket/api/v1/forms', wallet.inkey, data) .request('POST', '/lnticket/api/v1/forms', wallet.inkey, data)
.then(function(response) { .then(function (response) {
self.forms.push(mapLNTicket(response.data)) self.forms.push(mapLNTicket(response.data))
self.formDialog.show = false self.formDialog.show = false
self.formDialog.data = {} self.formDialog.data = {}
}) })
.catch(function(error) { .catch(function (error) {
LNbits.utils.notifyApiError(error) LNbits.utils.notifyApiError(error)
}) })
}, },
updateformDialog: function(formId) { updateformDialog: function (formId) {
var link = _.findWhere(this.forms, {id: formId}) var link = _.findWhere(this.forms, {id: formId})
console.log(link.id)
this.formDialog.data.id = link.id this.formDialog.data.id = link.id
this.formDialog.data.wallet = link.wallet this.formDialog.data.wallet = link.wallet
this.formDialog.data.name = link.name this.formDialog.data.name = link.name
@ -387,10 +389,9 @@
this.formDialog.data.costpword = link.costpword this.formDialog.data.costpword = link.costpword
this.formDialog.show = true this.formDialog.show = true
}, },
updateForm: function(wallet, data) { updateForm: function (wallet, data) {
var self = this var self = this
console.log(data) console.log('update', data)
LNbits.api LNbits.api
.request( .request(
'PUT', 'PUT',
@ -398,47 +399,47 @@
wallet.inkey, wallet.inkey,
data data
) )
.then(function(response) { .then(function (response) {
self.forms = _.reject(self.forms, function(obj) { self.forms = _.reject(self.forms, function (obj) {
return obj.id == data.id return obj.id == data.id
}) })
self.forms.push(mapLNTicket(response.data)) self.forms.push(mapLNTicket(response.data))
self.formDialog.show = false self.formDialog.show = false
self.formDialog.data = {} self.formDialog.data = {}
}) })
.catch(function(error) { .catch(function (error) {
LNbits.utils.notifyApiError(error) LNbits.utils.notifyApiError(error)
}) })
}, },
deleteForm: function(formsId) { deleteForm: function (formsId) {
var self = this var self = this
var forms = _.findWhere(this.forms, {id: formsId}) var forms = _.findWhere(this.forms, {id: formsId})
LNbits.utils LNbits.utils
.confirmDialog('Are you sure you want to delete this form link?') .confirmDialog('Are you sure you want to delete this form link?')
.onOk(function() { .onOk(function () {
LNbits.api LNbits.api
.request( .request(
'DELETE', 'DELETE',
'/lnticket/api/v1/forms/' + formsId, '/lnticket/api/v1/forms/' + formsId,
_.findWhere(self.g.user.wallets, {id: forms.wallet}).inkey _.findWhere(self.g.user.wallets, {id: forms.wallet}).inkey
) )
.then(function(response) { .then(function (response) {
self.forms = _.reject(self.forms, function(obj) { self.forms = _.reject(self.forms, function (obj) {
return obj.id == formsId return obj.id == formsId
}) })
}) })
.catch(function(error) { .catch(function (error) {
LNbits.utils.notifyApiError(error) LNbits.utils.notifyApiError(error)
}) })
}) })
}, },
exportformsCSV: function() { exportformsCSV: function () {
LNbits.utils.exportCSV(this.formsTable.columns, this.forms) LNbits.utils.exportCSV(this.formsTable.columns, this.forms)
} }
}, },
created: function() { created: function () {
if (this.g.user.wallets.length) { if (this.g.user.wallets.length) {
this.getTickets() this.getTickets()
this.getForms() this.getForms()

View File

@ -1,5 +1,6 @@
from quart import g, abort, render_template from quart import g, abort, render_template
from lnbits.core.crud import get_wallet
from lnbits.decorators import check_user_exists, validate_uuids from lnbits.decorators import check_user_exists, validate_uuids
from http import HTTPStatus from http import HTTPStatus
@ -20,10 +21,13 @@ async def display(form_id):
if not form: if not form:
abort(HTTPStatus.NOT_FOUND, "LNTicket does not exist.") abort(HTTPStatus.NOT_FOUND, "LNTicket does not exist.")
wallet = await get_wallet(form.wallet)
return await render_template( return await render_template(
"lnticket/display.html", "lnticket/display.html",
form_id=form.id, form_id=form.id,
form_name=form.name, form_name=form.name,
form_desc=form.description, form_desc=form.description,
form_costpword=form.costpword, form_costpword=form.costpword,
form_wallet=wallet.inkey
) )