WIP Verify and respond to zap requests
All checks were successful
continuous-integration/drone/push Build is passing

This commit is contained in:
2024-04-16 19:13:10 +02:00
parent 77e2fe5792
commit c3b82fc2a9
5 changed files with 407 additions and 31 deletions

View File

@@ -43,7 +43,7 @@ class LnurlpayController < ApplicationController
# GET /lnurlpay/:username/invoice
def invoice
amount = params[:amount].to_i / 1000 # msats
amount = params[:amount].to_i / 1000 # msats to sats
comment = params[:comment] || ""
address = @user.address
@@ -52,33 +52,19 @@ class LnurlpayController < ApplicationController
return
end
if !valid_comment?(comment)
render json: { status: "ERROR", reason: "Comment too long" }
return
if params[:nostr].present?
handle_zap_request amount, params[:nostr], params[:lnurl]
else
handle_pay_request address, amount, comment
end
memo = "To #{address}"
memo = "#{memo}: \"#{comment}\"" if comment.present?
payment_request = @user.ln_create_invoice({
amount: amount, # we create invoices in sats
memo: memo,
description_hash: Digest::SHA2.hexdigest(metadata(address)),
})
render json: {
status: "OK",
successAction: {
tag: "message",
message: "Sats received. Thank you!"
},
routes: [],
pr: payment_request
}
end
private
def check_service_available
http_status :not_found unless Setting.lndhub_enabled?
end
def find_user
@user = User.where(cn: params[:username], ou: Setting.primary_domain).first
http_status :not_found if @user.nil?
@@ -88,6 +74,10 @@ class LnurlpayController < ApplicationController
"[[\"text/identifier\", \"#{address}\"], [\"text/plain\", \"Send sats, receive thanks.\"]]"
end
def zap_metadata(event)
"[[\"application/json\", #{event.to_json}]]"
end
def valid_amount?(amount_in_sats)
amount_in_sats <= MAX_SATS && amount_in_sats >= MIN_SATS
end
@@ -96,9 +86,63 @@ class LnurlpayController < ApplicationController
comment.length <= MAX_COMMENT_CHARS
end
private
def handle_pay_request(address, amount, comment)
if !valid_comment?(comment)
render json: { status: "ERROR", reason: "Comment too long" }
return
end
def check_service_available
http_status :not_found unless Setting.lndhub_enabled?
memo = "To #{address}"
memo = "#{memo}: \"#{comment}\"" if comment.present?
payment_request = @user.ln_create_invoice({
amount: amount, # sats
memo: memo,
description_hash: Digest::SHA2.hexdigest(metadata(address)),
})
render json: {
status: "OK",
successAction: {
tag: "message",
message: "Sats received. Thank you!"
},
routes: [],
pr: payment_request
}
end
def nostr_event_from_payload(nostr_param)
event_obj = JSON.parse(nostr_param).transform_keys(&:to_sym)
Nostr::Event.new(**event_obj)
rescue => e
return nil
end
def valid_zap_request?(amount, event, lnurl)
NostrManager::VerifyZapRequest.call(
amount: amount, event: event, lnurl: lnurl
)
end
def handle_zap_request(amount, nostr_param, lnurl_param)
event = nostr_event_from_payload(nostr_param)
unless event.present? && valid_zap_request?(amount*1000, event, lnurl_param)
render json: { status: "ERROR", reason: "Invalid zap request" }
return
end
# TODO
# raise zap_metadata(event).inspect
payment_request = @user.ln_create_invoice({
amount: amount, # sats
# TODO should be npub instead of address?
memo: "Zapped #{@user.address} on Nostr", # TODO include event ID if given
description_hash: Digest::SHA2.hexdigest(zap_metadata(event)),
})
render json: { status: "OK", pr: payment_request }
end
end