withdraw/config.json
Padreug 9c0e58a87c
Some checks failed
lint.yml / feat: merge a link's `extra` into the payout payment (v1.2.2-aio.2) (pull_request) Failing after 0s
lint.yml / feat: merge a link's `extra` into the payout payment (v1.2.2-aio.2) (push) Failing after 0s
feat: merge a link's extra into the payout payment (v1.2.2-aio.2)
Adds an optional `extra` (JSON) field to a withdraw link. When the link
is claimed, that `extra` is merged onto the payout payment's `extra`, so
a caller can tag the resulting payment with metadata an external listener
keys on — the link is the only place to attach it (the customer-facing
LNURL-withdraw payout otherwise carries just `{tag, withdrawal_link_id}`).

Motivating use: bitSpire cash-in settlements. The operator's spirekeeper
listener fires a `cash_in` settlement (fee split to the platform) only on
an outbound payment stamped `source=bitspire`; before this there was no
way to stamp an LNURL-withdraw payout, so cash-ins never settled. bitSpire
now creates the cash-in link for the NET amount with
`extra={source, type:cash_in, principal_sats, fee_sats, ...}` and the
settlement fires on claim.

- models: `extra: dict | None` on CreateWithdrawData + WithdrawLink.
  LNbits' db layer (de)serializes dict columns to/from JSON natively
  (same as Payment.extra) — no per-field validator needed.
- migrations_fork.py: `withdraw_link.extra TEXT` under `withdraw_fork`,
  keeping the upstream-tracked migrations.py byte-identical for clean
  rebases (aiolabs/lnbits#8 pattern).
- views_lnurl: `extra={**(link.extra or {}), "tag": ..., "withdrawal_link_id": ...}`
  — the withdraw extension's own keys are written last so a caller cannot
  clobber them.

Verified end-to-end on the dev stack: a stamped link's payout carries the
merged extra and drives a spirekeeper cash_in settlement + super-fee payout.
2026-06-21 17:26:14 +02:00

80 lines
2.1 KiB
JSON

{
"name": "Withdraw Links",
"short_description": "Make LNURL withdraw links",
"tile": "/withdraw/static/image/lnurl-withdraw.png",
"version": "1.2.2-aio.2",
"min_lnbits_version": "1.3.0",
"contributors": [
{
"name": "arcbtc",
"uri": "https://github.com/arcbtc",
"role": "Developer"
},
{
"name": "talvasconcelos",
"uri": "https://github.com/talvasconcelos",
"role": "Developer"
},
{
"name": "eillarra",
"uri": "https://github.com/eillarra",
"role": "Developer"
},
{
"name": "dni",
"uri": "https://github.com/dni",
"role": "Developer"
},
{
"name": "motorina0",
"uri": "https://github.com/motorina0",
"role": "Developer"
},
{
"name": "prusnak",
"uri": "https://github.com/prusnak",
"role": "Developer"
},
{
"name": "callebtc",
"uri": "https://github.com/callebtc",
"role": "Developer"
},
{
"name": "Liongrass",
"uri": "https://github.com/Liongrass",
"role": "Developer"
},
{
"name": "supiiik",
"uri": "https://github.com/supiiik",
"role": "Developer"
},
{
"name": "Jakub-Dv",
"uri": "https://github.com/Jakub-Dv",
"role": "Developer"
}
],
"images": [
{
"uri": "https://raw.githubusercontent.com/lnbits/withdraw/main/static/image/1.jpg",
"link": "https://www.youtube.com/embed/TUmsHpJtveQ?si=3_l1cg0JC8CXHtYf"
},
{
"uri": "https://raw.githubusercontent.com/lnbits/withdraw/main/static/image/1.png"
},
{
"uri": "https://raw.githubusercontent.com/lnbits/withdraw/main/static/image/2.png"
},
{
"uri": "https://raw.githubusercontent.com/lnbits/withdraw/main/static/image/3.png"
},
{
"uri": "https://raw.githubusercontent.com/lnbits/withdraw/main/static/image/4.png"
}
],
"description_md": "https://raw.githubusercontent.com/lnbits/withdraw/main/description.md",
"terms_and_conditions_md": "https://raw.githubusercontent.com/withdraw/lnurldevice/main/toc.md",
"license": "MIT"
}