Skip to content

Confirm new expenses with a “View” toast on Spend instead of scrolling to and highlighting the row #91408

Open
10 of 10 issues completed

Description

@mountiny

Coming from here and also stemming from this disucssion

Background

When a user creates an expense from the global create FAB (or any flow that lands them on the Spend page), New Expensify confirms the expense was saved by navigating to Reports > Expense, finding the new row in the sorted/grouped FlashList, scrolling to it, and running a Reanimated worklet that fades its background. Producing that visible effect chains together navigation readiness, screen mount, deferred API writes, deferred heavy sort/group work, snapshot delivery, FlashList mount, and an onLayout-driven scrollToIndex — and two unrelated 300ms timers in useSearchHighlightAndScroll clear the orchestration state regardless of whether any of that has finished. Optimistic rows are placed at the bottom of page 1, then re-placed at their true sorted position once the server snapshot arrives, which routinely falls on a later page. The same logic produces meaningfully different observable behaviour on web, Android, and iOS, because every stage in the chain (navigation timing, InteractionManager, FlashList native engine, Reanimated scheduling) behaves differently per platform — see my case-by-case investigation (cases 1a/1b/2a/2b) in the issue thread.

Problem

When a user creates an expense from a flow that lands on the Spend page, if the new row is not present at its final sorted position in the rendered FlashList within ~300ms, then the row is neither scrolled to nor highlighted, leaving the user with no visual confirmation that the expense was created.

Solution

After the optimistic write is queued, fire a single toast — built on the existing GrowlNotification already mounted globally — that says “Expense created.” with a trailing View link, and remove the scroll-and-highlight choreography from Spend on every platform.

GrowlNotification is rendered at the root of the tree and animated by Reanimated on the UI thread, so its appearance has no dependency on the Spend list mounting, the snapshot loading, sort order being final, or onLayout firing within any deadline. Because the trigger fires synchronously with the optimistic write, the user sees the confirmation before the navigation pipeline finishes, and the View link reaches the new expense by transactionID directly — bypassing the “find a moving target in a paginated, re-sorting list” problem entirely. Visual treatment, position, and link styling follow the design discussion in the issue thread

Issue OwnerCurrent Issue Owner: @situchan

Activity

  1. melvin-bot commented on May 22, 2026

    @melvin-bot

    Current assignee @shawnborton is eligible for the NewFeature assigner, not assigning anyone new.

  2. borys3kk commented on May 25, 2026

    @borys3kk
    Contributor

    Hello, current state of the issue is that the main flow is working nicely on web app (in both desktop and mobile environment) and right now I'm fixing the issue with displaying the toast properly on mobile platforms (the "View" button is moved out of growl container):

    Image
  3. melvin-bot commented on May 28, 2026

    @melvin-bot

    @borys3kk Uh oh! This issue is overdue by 2 days. Don't forget to update your issues!

  4. borys3kk commented on May 29, 2026

    @borys3kk
    Contributor

    Not overdue, issue is being discussed in the PR, also looking for solution to no navigation bug in cold start

  5. melvin-bot commented on Jun 1, 2026

    @melvin-bot

    @borys3kk Whoops! This issue is 2 days overdue. Let's get this updated quick!

  6. 150 remaining items

  7. changed the title [-][Due for payment 2026-10-12] Confirm new expenses with a “View” toast on Spend instead of scrolling to and highlighting the row[/-] [+]Confirm new expenses with a “View” toast on Spend instead of scrolling to and highlighting the row[/+] on Oct 14, 2026
  8. removed their assignment
    on Oct 14, 2026
  9. mallenexpensify commented on Oct 14, 2026

    @mallenexpensify
    Contributor

    Please comment and tag me if/when payment is due, thx

  10. melvin-bot commented on Oct 19, 2026

    @melvin-bot

    @situchan Huh... This is 4 days overdue. Who can take care of this?

  11. melvin-bot commented on Oct 21, 2026

    @melvin-bot

    @situchan Still overdue 6 days?! Let's take care of this!

  12. situchan commented on Oct 23, 2026

    @situchan
    Contributor

    @MelvinBot suggest compensation amount based on size of PRs, number of commits, comments and discussions, scope changes during work, complexity, followup issues fixes, production bug fixes

    v1: #96496 (followup issues: #99248, #99252, #99255, #99257, #99261, #99262, #99264)
    v2: #100015 (followup issues: #102831, #102833, #102848, #102850, #102857, #102889)
    Fixing the bugs happening on production: #99249, #99253, #99258, #102845, #102945

  13. MelvinBot commented on Oct 23, 2026

    @MelvinBot
    Contributor

    I suggest $2,000 for situchan's C+ review on this issue. That's 8× the standard $250 review rate. Both contributors are contractors, so situchan is the only person to pay here.

    Work reviewed Size and effort Suggested
    [No QA] Growl: add action button and loading variant +309/−153, 12 files, 18 commits. Listed as $250 in the July payment summary. $250
    v1: Confirm new expenses with a “View” toast instead of scrolling to and highlighting the row +786/−948, 54 files, 55 commits, 55 PR comments. situchan left 5 reviews, 10 comments, and 7 inline comments. A contributor handoff changed the approach mid-review. $500
    v1 revert, then follow-up triage Reviewed the 54-file revert. Checked all 10 v1 deploy blockers against v2 and marked 3 as not bugs. included in v2
    v2: Confirm new expenses with a “View” toast instead of scrolling to and highlighting the row v2 +1,342/−1,223, 69 files, 39 commits. Full regression retest across web, mWeb, and Android. $750
    6 v2 follow-up fix PRs Reviewed and approved all 6. Most are small; one is +257 lines. $250
    Production bugs fixed along the way 99249, 99253, 99258, and 102845 were already happening on production and were verified fixed in v2. $250
    Total $2,000

    An internal engineer should still confirm two points before payment:

    • Regression penalty. The contributor guidelines cut C+ pay by 50% for each regression that review should have caught. v1 had 7 deploy blockers and v2 had 6. QA caught all of them on staging, and v1 was reverted before it reached production. Whether they count as regressions is a call for the internal team.
    • Avoid double payment. Android-Expense-Report name shows "Chat Report" briefly on expense opened offline via growl is still open, with its own fix PR and mollfpr as C+. I left it out of the total. If any follow-up issue pays situchan separately, take that amount off here.
    Follow-up PRs and issues counted

    v2 follow-up PRs, all by mhawryluk and approved by situchan:

    v1 deploy blockers checked in v2: #99248, #99252 (not a bug), #99255, #99257, #99261 (not a bug), #99262 (not a bug), #99264, plus the production bugs #99249, #99253, and #99258.

    Timeline: situchan started reviewing on 2026-07-03, v1 merged on 2026-08-21, v2 merged on 2026-10-01, and the last follow-up fixes merged in October. That's about 3.5 months of review.

  14. situchan commented on Oct 23, 2026

    @situchan
    Contributor

    Price increase request

    • Preparation (Growl components refactor - #94865): $250
    • Main feature PR: $1000
    • Followup fixes (across 6 PRs): $500
    • 4 production bug fixes: $500
    • Regression penalty: -$500 (all reported deploy blockers came from new feature itself, not breaking existing prod app)

    Melvin suggested: $2000

    I suggest Total: $1750

    cc: @mountiny

  15. situchan commented on Oct 23, 2026

    @situchan
    Contributor

    Regression Test Proposal

    Test 1: Growl from global create (Inbox and Spend)

    1. Go to Inbox.
    2. Open FAB > Create expense > Manual. Enter an amount, select the workspace and tap Create expense.
    3. Verify an "Expense added" growl with a "View" button appears.
    4. Repeat steps 2-3 with Scan, Distance and Per diem.
    5. Go to Spend and create another manual expense from FAB.
    6. Verify the same growl appears and no row in the table is highlighted.

    Test 2: View opens the right destination

    1. In Spend, create an expense from FAB and tap View on the growl.
    2. Verify the expense details open in the RHP over Spend.
    3. In Inbox (narrow layout), create an expense from FAB and tap View.
    4. Verify the expense thread opens full screen.
    5. In Inbox (wide layout), create an expense into a workspace report that already has 1+ expenses and tap View.
    6. Verify the expense report opens with the new expense's RHP on top and arrow navigation is visible in the header.
    7. In Inbox (wide layout), create an expense into a workspace report with no other expenses and tap View.
    8. Verify the expense details open directly in the RHP.
    9. With an expense already open in the RHP, create another expense from FAB and tap View.
    10. Verify the RHP is replaced, not stacked.
    11. Create an expense, switch to another tab before tapping View, then tap View.
    12. Verify navigation matches the tab you are now on.

    Test 3: Self DM, invoice, per diem with submissions disabled

    1. Create an expense from FAB with yourself as the recipient. Tap View.
    2. Verify the transaction thread opens full screen.
    3. Open the self DM chat and tap the same expense preview.
    4. Verify the expense opens correctly.
    5. Open FAB > Send invoice and send an invoice to any user.
    6. Verify the growl reads "Invoice sent" and View opens the invoice.
    7. Disable Submissions in the workspace Workflows settings.
    8. Open FAB > Create expense > Per diem and create an expense.
    9. Verify the "Expense added" growl appears.

    Test 4: Batch flows show one growl for the last expense

    1. Create a Scan expense for a recipient so the FAB shows a "Scan receipt" quick action.
    2. Use that quick action to upload 2 receipts.
    3. Verify the app navigates once and exactly one growl appears. View opens the last receipt's expense.
    4. In Spend, select 2+ expenses > "n selected" dropdown > Duplicate expenses.
    5. Verify one growl appears. View opens the last duplicated expense.
    6. Open an expense in Spend > More > Split > split into 2 and Save.
    7. Verify one growl appears. View opens the last split expense.
    8. (Native only) Share an image into Expensify from another app and submit it as an expense.
    9. Verify one growl appears and the app navigates once.

    Test 5: No growl where the user already sees the expense list

    1. Go to a workspace chat and create an expense.
    2. Open the expense from Inbox > More > Split > Save.
    3. Verify no growl appears.
    4. Create a new empty report. Open FAB > Create expense > Manual, select that report in the Report field and tap Create expense while the report is open.
    5. Verify no growl appears.
    6. Open a 1:1 DM and split an expense with that user. Then use the Split manual, Split scan and Split distance quick actions from FAB.
    7. Verify no growl appears for any of them.
    8. Go to a workspace chat, create an expense, open it and send a message in its thread.
    9. Close the report, reopen the expense from the LHN, then More > Split > Save.
    10. Verify no growl appears.
    11. In the self DM, create an expense. Open it from Home > Recently added, then More > Split > Save.
    12. Verify no growl appears.

    Test 6: Navigation and UI around the growl

    1. Go to a workspace chat. Open the Concierge side panel and create an expense from FAB.
    2. Close the side panel.
    3. Verify the growl is visible on top.
    4. From Inbox, create an expense from FAB. Tap View, then More > Split > Save.
    5. Verify the app does not jump back to the workspace chat.
    6. From the LHN, create an expense into a workspace chat and quickly tap its preview. Tap View on the growl.
    7. Verify View only closes the growl. Tap back 3 times and verify you land on the LHN without the expense reopening.
    8. Open Home > Recently added > an expense > More > Split > Save. Tap View, close the expense RHP, then on the report RHP tap More > Delete.
    9. Verify the central pane returns to the workspace chat.
    10. In Spend, select an expense, then Duplicate expense. Select an expense again, open the dropdown menu and tap View on the growl.
    11. Verify the dropdown menu closes.
    12. Enable high contrast in Account > Preferences > Theme and create an expense.
    13. Verify the View link on the growl is underlined.

    Test 7: Offline, delete invoice

    1. Go offline. Open FAB > Send invoice and send it to any user.
    2. Right click the invoice preview > Delete > Delete. Tap View on the growl.
    3. Verify nothing happens and no skeleton loader report opens.

    Test 8: Opening an expense or invoice via the growl behaves like opening it from the chat

    1. Open FAB > Send invoice and send an invoice to any user. Tap View on the "Invoice sent" growl.
    2. Verify no Join button appears on the invoice report.
    3. From Inbox, create 2 manual expenses from FAB into the same workspace chat. Tap View on the second growl.
    4. Tap More > Delete > Delete.
    5. Verify you land on the parent report, not the workspace chat.
    6. Create another expense from FAB into the same workspace chat and tap View. Tap the expense header to open the details page and delete the expense from there.
    7. Verify you land on the parent report again, matching step 5.

    Test 9: Offline, opened via the growl

    1. Create a manual expense from FAB into a workspace chat.
    2. Go offline. Create a second expense from FAB into the same workspace chat and tap View on the growl.
    3. Verify the header shows the expense name (a brief skeleton is fine) and never shows "Chat Report".
    4. Go back and tap the expense preview in the workspace chat.
    5. Verify the header again never shows "Chat Report".
    6. Still offline, create a manual expense from FAB and tap View on the growl.
    7. Tap More > Move to report > Create report.
    8. Verify the workspace avatar stays in the report header.

    Do we agree 👍 or 👎?

  16. melvin-bot commented on Oct 26, 2026

    @melvin-bot

    @situchan Whoops! This issue is 2 days overdue. Let's get this updated quick!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Labels

Type

No type

Projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions