skip to Main Content

My code is:

import { type } from '@testing-library/user-event/dist/type';
import React, { useState } from 'react';
import './clint.css'

export default function Addtask() {
  const [task, setTask] = useState([]);
  const [text, setText] = useState('');
  const obj = [{ task: text.trim(), id: task.length }];

  const handleSubmit = async (event) => {
    event.preventDefault();
    try {
      setTask([...task, obj[obj.length-1].task]);
      const resp = await fetch(
        'http://localhost:5000/addtask',
        {
          method: 'POST',
          body: JSON.stringify(task),
          headers: {
            'content-type': 'application/json'
          }
        }
      );
      if (resp.status === 200) {
        console.log('task added successfully');
      } else {
        console.log("unable to post");
      }          
    } catch(error) {
      console.log("error");
    }
  }

  function change(e) {
    const ip = e.target.value;
    setText(ip);
  }

  return (
    <div>
      <h1>add user component</h1>
 
      <span>Add Task</span>
      <input onChange={change} placeholder='add a task' />
      <button type='submit' onClick={handleSubmit}>submit</button>
      <ul>
        {task.map((tasks, i) => 
          <li key={i}>
            {tasks}
            <button
              className='delete'
              onClick={() => {
                const removeItem = task.filter(() => {
                  return obj[i].id !==  i;
                });
                setTask(removeItem);
                console.log(i)
              }}
            >
              <b>X</b>
            </button>
          </li>
        )}                
      </ul>
    </div>
  )
}

The error is coming:

Cannot read properties of undefined (reading 'id')
TypeError: Cannot read properties of undefined (reading 'id')
  at http://localhost:3000/main.158d69bbe90ec71b22a6.hot-update.js:94:29
  at Array.filter (<anonymous>)
  at onClick (http://localhost:3000/main.158d69bbe90ec71b22a6.hot-update.js:93:37)
  at HTMLUnknownElement.callCallback (http://localhost:3000/static/js/bundle.js:29605:18)
  at Object.invokeGuardedCallbackDev (http://localhost:3000/static/js/bundle.js:29649:20)
  at invokeGuardedCallback (http://localhost:3000/static/js/bundle.js:29706:35)
  at invokeGuardedCallbackAndCatchFirstError 
(http://localhost:3000/static/js/bundle.js:29720:29)
  at executeDispatch (http://localhost:3000/static/js/bundle.js:33864:7)
  at processDispatchQueueItemsInOrder (http://localhost:3000/static/js/bundle.js:33890:11)
  at processDispatchQueue (http://localhost:3000/static/js/bundle.js:33901:9)

Why am I not able to delete the tasks from the todo list? When I am clicking the ‘X’ icon to delete the tasks this error is coming saying that cannot read properties of undefined (reading ‘id’). I have tried many approaches but nothing is working properly in most of the cases this error is coming.

2

Answers


  1. the way i’ve found to get try to get a value when that happens is by using

    object?.value
    

    or by using

    object['value']
    

    those have helped me in the past, good luck with the problem

    Login or Signup to reply.
  2. Issue

    obj is declared each render cycle and is an array with only 1 element, e.g. it’s an array of length 1. When the tasks array is mapped and you click the delete button of any task after index 0, then the i index value indexes out of bounds on the obj array. In other words, when i is any value other than 0, obj[i] is undefined and the code can’t access an id property of an undefined value.

    Solution

    If you are needing to remove an element from the task state array, then filter the tasks that have id property that isn’t the same as that of the task you would like removed. Also, since the task state is an array of tasks I highly recommend renaming it tasks so it’s clearer what its use case and purpose is.

    const [tasks, setTasks] = useState([]);
    
    ...
    
    <ul>
      {tasks.map((task) => (
        <li key={task.id}> // <-- use task id as React key
          {task.task}      // <-- task is object, task.task is text
          <button
            className='delete'
            onClick={() => {
              // filter all tasks that have a different id than this task
              setTask(tasks => tasks.filter(taskEl => taskEl.id !== task.id));
            }}
          >
            <b>X</b>
          </button>
        </li>
      )}                
    </ul>
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search