'React forms. Trouble using setState after .reset();

I have a form where the fields can be edited after submitted. For each "operation" on my table that displays all objects inside an array of operations (I call it operationsLog), I have an edit button that makes the input fields editable for a given object.

{
  "operations": [       
    {
       "id": 1,
       "name": "Bitcoin",
       "ticker": "BTC-USD",        
       "price": 100,
       "currency": "USD",
       "qty": 0.1,
       "operationType": "sell",
       "date": "01/06/2021",
       "fee": 5,
       "bank": "Binance"
     },
     {
       "id": 2,
       "name": "Cardano",
       "ticker": "ADA-USD",
       "price": 120,
       "currency": "NOK",
       "qty": 20,
       "operationType": "sell",
       "date": "07/07/2021",
       "fee": 3,
       "bank": "Binance"
     }
   ]
}

When the user clicks on the editing button, the input fields become editable via the setEditOperation() state hook that receives the id of the operation, making it editable. The new user input is temporarily stored in an object (tempOperation) as the user types, by using the onChange property. Then, when the user clicks on the save button, the tempOperation object replaces the previous object stored in the operationsLog array, and the setEditOperation() recives the value null, disabling the input fields.

 const [operationsLog, setOperationsLog] = useState(operationsLogFile.operations);

//edit operation inside operationsLog
  const [editOperation, setEditOperation] = useState(null);

  const handleEditClick = (event, operation) => {
    event.preventDefault();

    setEditOperation(operation.id);

    const opValues = {
      id: operation.id,
      ticker: operation.ticker,
      price: operation.price,
      currency: operation.currency,
      qty: operation.qty,
      operationType: operation.operationType,
      date: operation.date,
      fee: operation.fee,
      bank: operation.bank
    }
    setTempOperation(opValues);
  }

  const [tempOperation, setTempOperation] = useState({
    id: '',
    ticker: '',
    price: '',
    currency: '',
    qty: '',
    operationType: '',
    date: '',
    fee: '',
    bank: ''
  })

  const handleEditOperationChange = (event) => {
    event.preventDefault();

    const fieldName = event.target.getAttribute('name');
    const fieldValue = event.target.value;

    const newOperationData = { ...tempOperation }
    newOperationData[fieldName] = fieldValue;

    setTempOperation(newOperationData);

  }

  const handleEditOperationSubmit = (event) => {
    event.preventDefault();

    const editedOperation = {
      id: tempOperation.id,
      name: tempOperation.name,
      ticker: tempOperation.ticker,
      price: tempOperation.price,
      currency: tempOperation.currency,
      qty: tempOperation.qty,
      operationType: tempOperation.operationType,
      date: tempOperation.date,
      fee: tempOperation.fee,
      bank: tempOperation.bank
    }
    const newOperationsLog = [...operationsLog];

    const index = operationsLog.findIndex((operation) => operation.id === editedOperation.id)

    newOperationsLog[index] = editedOperation;

    setOperationsLog(newOperationsLog);
    setEditOperation(null)
  }

Up to here the code works fine as it should. My problem is with the "cancel button". I want to give the user the opportunity to, while editing an operation, click cancel and discard all changes made, leaving the operation as it originally was. To do that, I'm calling handleCancelClick() when the cancel button is clicked, which passes the original operation data through. Then I set the tempOperation identical to the original operation (this is just to prevent a bug when clicking on editing again), reset the input fields using the id of the object that contains them, and disable the fields by using the setEditOperation(), which receives the value null.

 // cancel edit operation    
    const handleCancelClick = (operation) => {
         
    const originalOp = {
      id: operation.id,
      ticker: operation.ticker,
      price: operation.price,
      currency: operation.currency,
      qty: operation.qty,
      operationType: operation.operationType,
      date: operation.date,
      fee: operation.fee,
      bank: operation.bank
    }
    
    setTempOperation(originalOp)

    var key = operation.id;
    document.getElementById({ key }).reset();

    setEditOperation(null)
  }
  

The funny thing is that document.getElementById({ key }).reset(); does reset the display to the original values, and keeps consistent in the operationsLog, and the setEditOperation(null) does disable the input fields for editing, but they don't work after each other.

setEditOperation(null) does not work after document.getElementById({ key }).reset();. The fields are reset to the original values but they continue being editable. The state keeps storing the id of the object that was being edited, and not null. But if I comment the document.getElementById({ key }).reset();, then the setEditOperation(null) works as it should.

What am I missing?



Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source