Skip to content

Bug: state updates are applied out of order inside useEffect when using Promise.resolve #24649

@Dremora

Description

@Dremora

When two state updates are scheduled within useEffect, first one directly and second wrapped inside Promise.resolve(), they will be applied out of order. Same behaviour when using queueMicrotask instead. setTimeout(x, 0) doesn't produce the issue.

React version: 18.1.0

This is only happening in Concurrent Mode with createRoot.

This is based on a real-world scenario arising from certain patterns of usage of react-query (which internally calls Promise.resolve()) and useTransition.

Steps To Reproduce

  1. Open Codesandbox
  2. Click the button
  3. Watch logs in the console

Link to code example: https://codesandbox.io/s/react-state-order-bug-o4izk6?file=/src/App.js:264-265

The current behavior

Console output after button press:

{submitCount: 0, isSubmitScheduled: true}
{submitCount: 1, isSubmitScheduled: true}
{submitCount: 1, isSubmitScheduled: false}

The expected behavior

Console output after button press:

{submitCount: 0, isSubmitScheduled: true}
{submitCount: 0, isSubmitScheduled: false}
{submitCount: 1, isSubmitScheduled: false}

Alternatively, if the updates should have been batched (I'm not sure whether batching should apply here), then the expected output would be):

{submitCount: 0, isSubmitScheduled: true}
{submitCount: 1, isSubmitScheduled: false}

update: now that I've discovered that this applies to microtasks as well, the issue might be related to #24625.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Resolution: StaleAutomatically closed due to inactivityStatus: UnconfirmedA potential issue that we haven't yet confirmed as a bug

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions