primereact icon indicating copy to clipboard operation
primereact copied to clipboard

DataTable => Column: onCellEditComplete is fired twice

Open Fallup opened this issue 1 year ago • 3 comments

Describe the bug

onCellEditComplete of the Column component in the DataTable is fired twice on version 10.5.1 Can be reproduced with the StackBlitz example directly from the docs.

This was working fine on version 9.6.4

Reproducer

https://stackblitz.com/edit/rb6yv7?file=src%2FApp.tsx

PrimeReact version

10.5.1

React version

18.x

Language

TypeScript

Build / Runtime

Vite

Browser(s)

No response

Steps to reproduce the behavior

Edit cell, click away and see that the onCellEditComplete is called twice.

Expected behavior

onCellEditComplete should be called only once

Fallup avatar Mar 13 '24 12:03 Fallup

looks like strict mode

kl-nevermore avatar Mar 22 '24 07:03 kl-nevermore

Any work around before the issue gets resolved? Thank you!

Chimi-RE avatar May 03 '24 12:05 Chimi-RE

Any work around before the issue gets resolved? Thank you!

The only workaround I found was to use useRef as a guard. Set it to true/false at the start/end of the onCellEditComplete callback and add a guard at the start of the callback, e.g.:

       ...
       const cellEditCompletePending = useRef(false)
       ...
      <Column
        onCellEditComplete={async (e) => {
              if (cellEditCompletePending.current) {
                  return
              }
              cellEditCompletePending.current = true
              // do stuff
              cellEditCompletePending.current = false
        }}
        />
        ...

Fallup avatar May 14 '24 20:05 Fallup

I have the same issue at 10.6.5 version but only onKeyDown. I was trying to debug it and see what is causing the function to be called twice but It seems to me that is something related with React... Could it be @melloware ?

BTW, cellEditValidator is also being calld twice. In fact this code inside this function is what is being called twice when onKeyDown event is fired:

https://github.com/primefaces/primereact/blob/463ba5c70b80127a535ae31e0f3bf2c00889a524/components/lib/datatable/BodyCell.js#L167-L196

The event is only fired once but the code inside setEditingRowDataState is being called twice.

The funny thing is that only happens if the value of the cell has been changed.

Edit

@kl-nevermore has right. I just found this issue on stackoverflow: https://stackoverflow.com/questions/62106596/reactjs-setstate-being-called-twice-in-a-function-called-once-why that references this https://github.com/facebook/react/issues/12856#issuecomment-390206425

It seems is that is the current behaviour of React, executing twice the setter callback when using React.StrictMode.

So my question is: Is it possible that React strictMode is being activated on production release?

Maybe a solution could be execute the code inside setEditingRowDataState at outside the setter, obtaining the prev by checking the component data reference and simply just return the newRowData. I don't know.

didix16 avatar May 19 '24 18:05 didix16

RP submitted use ref cached editingRowDataState

  • prevent warning of Cannot update a component while rendering a different component(#5556 ),call other setState in the callback of setState
  • switchCellToViewMode is triggered by useEventListener,but got stale value in listener
  • remove unnecessary timer

kl-nevermore avatar May 20 '24 08:05 kl-nevermore