# Receiver pre-filled from URL query param (?address=)

**URL:** https://ghostforum.org/t/receiver-pre-filled-from-url-query-param-address/152
**Category:** Bug Bounty
**Tags:** ghost-lite
**Created:** [October 6, 2026, 2:51am UTC](https://ghostforum.org/t/receiver-pre-filled-from-url-query-param-address/152 "2026-10-06T02:51:06Z")
**Posts on this page:** 3
**Page:** 1

<div class="post-metadata">

### Author: ![Rusdiwireng](https://ghostforum.org/letter_avatar_proxy/v4/letter/r/9de0a6/32.png) [@Rusdiwireng](https://ghostforum.org/u/Rusdiwireng)
#### Post date: [October 6, 2026, 2:51am UTC](https://ghostforum.org/t/receiver-pre-filled-from-url-query-param-address/152/1 "2026-10-06T02:51:06Z")

</div>

**Component:** `ghost-lite` @ `a420393`, `src/containers/Transactions.tsx:37-38,54`; internal trigger in `src/containers/AddressBook.tsx:127-130` (`openTransfer` → `navigate('/transactions?address=...')`).

**Description:** The Transactions page initializes the receiver state directly from the URL: `const initialReceiver = queryParams.get("address") ?? ""`. Anyone can craft a link `https://<app>/#/transactions?address=<attacker-SS58-address>` and lure the victim into pasting an amount and pressing Transfer. This is a by-design feature for the address book’s “Send” button, but it accepts input from arbitrary external links without distinction.

**Impact:** Social-engineering amplifier. Existing verified mitigations: (1) the full address is shown in the input (not truncated), (2) `receiverObject` validates the checksum via `ss58Decode` and the prefix must match the chain’s `ss58Format` (`Transactions.tsx:88-99`): calldata is not built for invalid addresses, (3) the wallet signing popup shows the real decode. Exploitation needs a victim who carelessly ignores a clearly displayed address.

**Reproduction:** Static: open `/#/transactions?address=<valid SS58>` → the receiver field auto-fills with the URL’s address.

**Severity: Low.** Reason: behavior verified, but the exploit chain needs heavy social engineering against three layers of visibility/validation.

**Recommendation:** When `address` comes from the query param (not internal address-book navigation), show a confirmation banner (“Receiver filled from link, verify the address”), or consume and strip the param from the URL (`navigate(..., {replace:true})`).

**Verification:** VERIFIED.

---

<div class="post-metadata">

### Author: ![VoidDragon](https://ghostforum.org/user_avatar/ghostforum.org/voiddragon/32/16_2.png) [@VoidDragon](https://ghostforum.org/u/VoidDragon)
#### Post date: [October 6, 2026, 9:42am UTC](https://ghostforum.org/t/receiver-pre-filled-from-url-query-param-address/152/2 "2026-10-06T09:42:14Z")

</div>

Thank you for your report!

But this small routing feature is expected to be used alongside sending a sort of _receive_ link. So for now it works as expected - at the same time, it does open up a social-engineering attack surface. What trade-offs would you recommend here?

---

<div class="post-metadata">

### Author: ![Rusdiwireng](https://ghostforum.org/letter_avatar_proxy/v4/letter/r/9de0a6/32.png) [@Rusdiwireng](https://ghostforum.org/u/Rusdiwireng)
#### Post date: [October 7, 2026, 7:24am UTC](https://ghostforum.org/t/receiver-pre-filled-from-url-query-param-address/152/3 "2026-10-07T07:24:03Z")

</div>

My recommended trade-off, keeping the receive-link feature intact:

1. Distinguish internal from external navigation. Today the address book’s Send button and an arbitrary external link both arrive as ?address= in the URL, so the app cannot tell them apart. Pass the address via router state for the internal Send flow, and treat a bare ?address= param (without router state) as external. External prefills get a dismissible banner: “Receiver filled from a link. Verify the address before sending.” Internal navigation shows no banner, so the normal UX is untouched.

2. Consume and strip the param. After reading ?address= on mount, navigate with replace:true to remove it from the URL. The prefill still works, but the address no longer sits in a copy-pasteable, forwardable link afterwards.

3. Keep what already works: full-address display, checksum validation, and the wallet decode popup. Those three are doing the real work today.

This keeps the one-click receive link working exactly as before for legitimate use, while an attacker-crafted link now announces itself instead of prefilling silently.
