fix: resolve LNURL-pay usernames case-insensitively (#3058)#3115
Open
protivon wants to merge 1 commit into
Open
fix: resolve LNURL-pay usernames case-insensitively (#3058)#3115protivon wants to merge 1 commit into
protivon wants to merge 1 commit into
Conversation
LNURL-pay (`/api/lnurlp/[username]` and `.../pay`) looked the recipient up
with `models.user.findUnique({ where: { name: username } })`. Despite `name`
being a Citext column, this lookup did not reliably fold case, so paying a
mixed-case Lightning address such as `SwapMarket@stacker.news` returned
"user does not exist" while `k00b@stacker.news` worked.
Use a case-insensitive lookup (`findFirst` with `mode: 'insensitive'`) in both
the LNURL-pay metadata route and the pay route so any casing of an existing
username resolves to the same account. No new users can be created by this, and
since `name` is unique+Citext there is at most one match.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Description
Fixes #3058. Paying a mixed-case Lightning address such as
SwapMarket@stacker.newsreturned "user@SwapMarketdoes not exist", while the lowercase form worked.Both LNURL-pay endpoints resolved the recipient with:
The
users.namecolumn isCitext, so equality in Postgres is case-insensitive — but Prisma'sfindUniqueon the unique key does not reliably fold case for the bound parameter here, so a mixed-caseusernamefrom the URL missed the row. The codebase already compensates for this elsewhere by comparing names with.toUpperCase()(seeapi/resolvers/user.js).This PR makes the two LNURL-pay lookups explicitly case-insensitive:
in
pages/api/lnurlp/[username]/index.js(the LNURL-pay metadata response) andpages/api/lnurlp/[username]/pay.js(the invoice/callback). Any casing of an existing username now resolves to the same account.Screenshots
N/A — server-side payment-resolution fix, no UI change.
Additional Context
nameis both@uniqueandCitext, so a case-insensitive match returns at most one row;findFirstis therefore equivalent tofindUniquefor valid data while tolerating casing. This cannot create users or change who an address maps to — it only lets an already-existing recipient be found regardless of the sender's casing.Checklist
Are your changes backward compatible? Please answer below:
Yes. Lowercase addresses behave exactly as before; only previously-failing mixed-case lookups now succeed. No schema, GraphQL, or API-shape changes.
On a scale of 1-10 how well and how have you QA'd this change and any features it might affect? Please answer below:
7/10. Verified the root cause by reading the schema (
name … @db.Citext, line 19 ofprisma/schema.prisma) and confirming both LNURL-pay routes used the case-sensitivefindUnique. Confirmedmode: 'insensitive'is supported on the project's Prisma 5.20findFirst. Both changed files passnode --check. I did not spin up the full stack to send a live mixed-case LNURL payment, so an end-to-end test against a running node would be the remaining QA step.For frontend changes: Tested on mobile, light and dark mode? Please answer below:
N/A — no frontend changes.