parent
35c20eda72
commit
e0ea0e30e7
7 changed files with 423 additions and 33 deletions
|
|
@ -27,7 +27,11 @@ window.PageEventsDisplay = {
|
|||
show: false,
|
||||
status: 'pending',
|
||||
paymentReq: null,
|
||||
isFiat: false
|
||||
isFiat: false,
|
||||
isOnchain: false,
|
||||
onchainAddress: null,
|
||||
onchainAmountSat: 0,
|
||||
mempoolEndpoint: null
|
||||
},
|
||||
paymentDismissMsg: null,
|
||||
paymentWebsocket: null
|
||||
|
|
@ -79,6 +83,32 @@ window.PageEventsDisplay = {
|
|||
},
|
||||
allowNostrNotifications() {
|
||||
return Boolean(this.event?.extra?.nostr_notifications)
|
||||
},
|
||||
allowOnchain() {
|
||||
return Boolean(this.event?.extra?.onchain_enabled)
|
||||
},
|
||||
showPaymentMethodSelector() {
|
||||
return this.allowFiatCheckout || this.allowOnchain
|
||||
},
|
||||
paymentMethodOptions() {
|
||||
const options = [{label: 'Lightning', value: 'lightning'}]
|
||||
if (this.allowFiatCheckout) {
|
||||
options.push({label: this.fiatCheckoutLabel, value: 'fiat'})
|
||||
}
|
||||
if (this.allowOnchain) {
|
||||
options.push({label: 'Bitcoin', value: 'onchain'})
|
||||
}
|
||||
return options
|
||||
},
|
||||
onchainPaymentUri() {
|
||||
if (!this.receive.onchainAddress) return ''
|
||||
const btc = (this.receive.onchainAmountSat / 100000000).toFixed(8)
|
||||
return `bitcoin:${this.receive.onchainAddress}?amount=${btc}`
|
||||
},
|
||||
mempoolAddressUrl() {
|
||||
if (!this.receive.onchainAddress || !this.receive.mempoolEndpoint)
|
||||
return null
|
||||
return `${this.receive.mempoolEndpoint}/address/${this.receive.onchainAddress}`
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
|
|
@ -131,7 +161,11 @@ window.PageEventsDisplay = {
|
|||
show: false,
|
||||
status: 'pending',
|
||||
paymentReq: null,
|
||||
isFiat: false
|
||||
isFiat: false,
|
||||
isOnchain: false,
|
||||
onchainAddress: null,
|
||||
onchainAmountSat: 0,
|
||||
mempoolEndpoint: null
|
||||
}
|
||||
},
|
||||
nameValidation(val) {
|
||||
|
|
@ -169,7 +203,11 @@ window.PageEventsDisplay = {
|
|||
show: false,
|
||||
status: 'complete',
|
||||
paymentReq: null,
|
||||
isFiat: false
|
||||
isFiat: false,
|
||||
isOnchain: false,
|
||||
onchainAddress: null,
|
||||
onchainAmountSat: 0,
|
||||
mempoolEndpoint: null
|
||||
}
|
||||
this.ticketLink = {
|
||||
show: true,
|
||||
|
|
@ -192,15 +230,18 @@ window.PageEventsDisplay = {
|
|||
promo_code: this.formDialog.data.promo_code || null,
|
||||
refund_address: this.formDialog.data.refund || null,
|
||||
nostr_identifier: this.formDialog.data.nostr_identifier || null,
|
||||
payment_method: this.allowFiatCheckout
|
||||
payment_method: this.showPaymentMethodSelector
|
||||
? this.formDialog.data.payment_method
|
||||
: 'lightning'
|
||||
}
|
||||
)
|
||||
const isFiat = Boolean(data.is_fiat)
|
||||
const isOnchain = Boolean(data.onchain_address)
|
||||
const isFiat = !isOnchain && Boolean(data.is_fiat)
|
||||
this.paymentReq = isFiat
|
||||
? data.fiat_payment_request || null
|
||||
: data.payment_request
|
||||
: isOnchain
|
||||
? null
|
||||
: data.payment_request
|
||||
this.paymentHash = data.payment_hash
|
||||
|
||||
this.paymentDismissMsg = Quasar.Notify.create({
|
||||
|
|
@ -211,7 +252,11 @@ window.PageEventsDisplay = {
|
|||
show: true,
|
||||
status: 'pending',
|
||||
paymentReq: this.paymentReq,
|
||||
isFiat
|
||||
isFiat,
|
||||
isOnchain,
|
||||
onchainAddress: data.onchain_address || null,
|
||||
onchainAmountSat: data.onchain_amount_sat || 0,
|
||||
mempoolEndpoint: data.onchain_mempool_endpoint || null
|
||||
}
|
||||
if (isFiat && this.paymentReq) {
|
||||
window.open(this.paymentReq, '_blank', 'noopener')
|
||||
|
|
|
|||
|
|
@ -80,20 +80,18 @@
|
|||
"
|
||||
></q-select>
|
||||
<div class="row q-col-gutter-md q-pt-lg items-center">
|
||||
<div v-if="allowFiatCheckout" class="col-auto">
|
||||
<div v-if="showPaymentMethodSelector" class="col-auto">
|
||||
<q-option-group
|
||||
v-model="formDialog.data.payment_method"
|
||||
inline
|
||||
:options="[
|
||||
{label: 'Lightning', value: 'lightning'},
|
||||
{
|
||||
label: fiatCheckoutLabel,
|
||||
value: 'fiat'
|
||||
}
|
||||
]"
|
||||
:options="paymentMethodOptions"
|
||||
></q-option-group>
|
||||
</div>
|
||||
<div :class="allowFiatCheckout ? 'col-12 col-md-3' : 'col-12'">
|
||||
<div
|
||||
:class="
|
||||
showPaymentMethodSelector ? 'col-12 col-md-3' : 'col-12'
|
||||
"
|
||||
>
|
||||
<q-input
|
||||
filled
|
||||
dense
|
||||
|
|
@ -140,7 +138,7 @@
|
|||
|
||||
<q-dialog v-model="receive.show" position="top" @hide="closeReceiveDialog">
|
||||
<q-card
|
||||
v-if="!receive.paymentReq"
|
||||
v-if="!receive.paymentReq && !receive.isOnchain"
|
||||
class="q-pa-lg q-pt-xl lnbits__dialog-card"
|
||||
>
|
||||
</q-card>
|
||||
|
|
@ -175,6 +173,51 @@
|
|||
<q-btn v-close-popup flat color="grey" class="q-ml-auto">Close</q-btn>
|
||||
</div>
|
||||
</q-card>
|
||||
<q-card
|
||||
v-else-if="receive.isOnchain"
|
||||
class="q-pa-lg q-pt-xl lnbits__dialog-card"
|
||||
>
|
||||
<div class="text-center q-mb-lg">
|
||||
<div class="text-h6 q-mb-sm">Pay with Bitcoin</div>
|
||||
<lnbits-qrcode
|
||||
:href="onchainPaymentUri"
|
||||
:value="onchainPaymentUri.toUpperCase()"
|
||||
></lnbits-qrcode>
|
||||
<div class="text-body1 q-mt-md">
|
||||
<strong
|
||||
>{{
|
||||
(receive.onchainAmountSat / 100000000).toFixed(8)
|
||||
}}
|
||||
BTC</strong
|
||||
>
|
||||
</div>
|
||||
<div
|
||||
class="text-caption text-grey q-mt-xs"
|
||||
style="word-break: break-all"
|
||||
>
|
||||
{{ receive.onchainAddress }}
|
||||
</div>
|
||||
</div>
|
||||
<div class="row q-mt-lg q-col-gutter-sm">
|
||||
<q-btn
|
||||
outline
|
||||
color="grey"
|
||||
@click="utils.copyText(receive.onchainAddress)"
|
||||
>Copy address</q-btn
|
||||
>
|
||||
<q-btn
|
||||
v-if="mempoolAddressUrl"
|
||||
outline
|
||||
color="grey"
|
||||
type="a"
|
||||
:href="mempoolAddressUrl"
|
||||
target="_blank"
|
||||
rel="noopener"
|
||||
>View on mempool</q-btn
|
||||
>
|
||||
<q-btn v-close-popup flat color="grey" class="q-ml-auto">Close</q-btn>
|
||||
</div>
|
||||
</q-card>
|
||||
<q-card v-else class="q-pa-lg q-pt-xl lnbits__dialog-card">
|
||||
<div class="text-center q-mb-lg">
|
||||
<lnbits-qrcode
|
||||
|
|
|
|||
|
|
@ -128,7 +128,8 @@ window.PageEvents = {
|
|||
promo_codes: []
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
onchainWallets: []
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
|
|
@ -136,6 +137,42 @@ window.PageEvents = {
|
|||
if (!value) return ''
|
||||
return value.length > 4 ? `${value.slice(0, 4)}...` : value
|
||||
},
|
||||
async loadOnchainWallets() {
|
||||
const wallet = _.findWhere(this.g.user.wallets, {
|
||||
id: this.formDialog.data.wallet
|
||||
})
|
||||
if (!wallet) return
|
||||
try {
|
||||
const {data} = await LNbits.api.request(
|
||||
'GET',
|
||||
'/events/api/v1/events/onchain/status',
|
||||
wallet.adminkey
|
||||
)
|
||||
this.onchainWallets = data.available ? data.wallets || [] : []
|
||||
} catch {
|
||||
this.onchainWallets = []
|
||||
}
|
||||
},
|
||||
async confirmOnchainTicket(ticket) {
|
||||
const wallet = _.findWhere(this.g.user.wallets, {id: ticket.wallet})
|
||||
if (!wallet) return
|
||||
try {
|
||||
await LNbits.api.request(
|
||||
'PUT',
|
||||
`/events/api/v1/tickets/${ticket.id}/onchain-confirm`,
|
||||
wallet.adminkey
|
||||
)
|
||||
Quasar.Notify.create({
|
||||
type: 'positive',
|
||||
message: 'Onchain payment confirmed.',
|
||||
icon: null
|
||||
})
|
||||
await this.getTickets()
|
||||
await this.getAllTickets()
|
||||
} catch (error) {
|
||||
LNbits.utils.notifyApiError(error)
|
||||
}
|
||||
},
|
||||
primaryTicketWave(data = this.formDialog.data) {
|
||||
if (!data.extra) data.extra = {}
|
||||
if (!data.extra.ticket_waves || data.extra.ticket_waves.length === 0) {
|
||||
|
|
@ -403,6 +440,8 @@ window.PageEvents = {
|
|||
min_tickets: 1,
|
||||
email_notifications: false,
|
||||
nostr_notifications: false,
|
||||
onchain_enabled: false,
|
||||
onchain_wallet_id: null,
|
||||
ticket_waves: [
|
||||
{
|
||||
id: 'primary',
|
||||
|
|
@ -425,6 +464,12 @@ window.PageEvents = {
|
|||
}
|
||||
}
|
||||
this.formDialog.show = true
|
||||
if (
|
||||
this.formDialog.data.wallet &&
|
||||
this.formDialog.data.extra?.onchain_enabled
|
||||
) {
|
||||
this.loadOnchainWallets()
|
||||
}
|
||||
},
|
||||
resetEventDialog() {
|
||||
this.formDialog.show = false
|
||||
|
|
@ -437,6 +482,8 @@ window.PageEvents = {
|
|||
min_tickets: 1,
|
||||
email_notifications: false,
|
||||
nostr_notifications: false,
|
||||
onchain_enabled: false,
|
||||
onchain_wallet_id: null,
|
||||
ticket_waves: [
|
||||
{
|
||||
id: 'primary',
|
||||
|
|
|
|||
|
|
@ -265,6 +265,18 @@
|
|||
>
|
||||
<q-tooltip>Resend ticket email</q-tooltip>
|
||||
</q-btn>
|
||||
<q-btn
|
||||
v-if="props.row.extra?.onchain && !props.row.paid"
|
||||
flat
|
||||
dense
|
||||
size="xs"
|
||||
@click="confirmOnchainTicket(props.row)"
|
||||
icon="currency_bitcoin"
|
||||
color="orange"
|
||||
class="q-ml-xs"
|
||||
>
|
||||
<q-tooltip>Confirm onchain payment</q-tooltip>
|
||||
</q-btn>
|
||||
</q-td>
|
||||
|
||||
<q-td v-for="col in props.cols" :key="col.name" :props="props">
|
||||
|
|
@ -602,6 +614,42 @@
|
|||
</div>
|
||||
</q-expansion-item>
|
||||
|
||||
<q-expansion-item
|
||||
group="advanced"
|
||||
icon="currency_bitcoin"
|
||||
label="Onchain payments"
|
||||
>
|
||||
<div class="q-mt-lg">
|
||||
<div class="text-caption q-mb-md">
|
||||
Accept Bitcoin onchain payments. Requires the Watchonly
|
||||
extension.
|
||||
</div>
|
||||
<q-toggle
|
||||
v-model="formDialog.data.extra.onchain_enabled"
|
||||
label="Accept onchain payments"
|
||||
left-label
|
||||
@update:model-value="val => val && loadOnchainWallets()"
|
||||
></q-toggle>
|
||||
<q-select
|
||||
v-if="formDialog.data.extra.onchain_enabled"
|
||||
filled
|
||||
dense
|
||||
class="q-mt-md"
|
||||
v-model="formDialog.data.extra.onchain_wallet_id"
|
||||
label="Watchonly wallet"
|
||||
:options="
|
||||
onchainWallets.map(w => ({
|
||||
label: w.title || w.id,
|
||||
value: w.id
|
||||
}))
|
||||
"
|
||||
emit-value
|
||||
map-options
|
||||
hint="Bitcoin watchonly wallet for receiving onchain payments"
|
||||
></q-select>
|
||||
</div>
|
||||
</q-expansion-item>
|
||||
|
||||
<div class="row q-mt-lg">
|
||||
<q-btn
|
||||
v-if="formDialog.data.id"
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue