'TypeError: Cannot set properties of undefined (setting 'duration')

I am getting this error when I am trying to add an answer although the error is negligible and my application works upon canceling the error and data is also getting saved in states and POST request is also happening. How to get rid of this?

Since on popping out of the error, I am able to perform my functionality accurately. Is there any way to track the issue or resolve it? thanks in advance.

import React, { useState } from "react";
import {
  Row,
  Col,
  Card,
  CardBody,
  FormGroup,
  Button,
  Label,
  Input,
  Container,
} from "reactstrap";
import { AvForm, AvField } from "availity-reactstrap-validation";
import RangeSlider from "react-bootstrap-range-slider";
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
import { faTimes } from "@fortawesome/free-solid-svg-icons";
import { connect } from "react-redux";
import { interviewAdd } from "../../redux/actions/interviewActions";
import Breadcrumbs from "../../components/Common/Breadcrumb";
import { Link, useHistory } from "react-router-dom";

const AddInterview = (props) => {
  const history = useHistory();
  const [breadcrumbItems, setBreadcrumbItems] = useState([
    { title: "Interview App", link: "#" },
    { title: "Interview Form", link: "#" },
  ]);
  const [name, setName] = useState("");
  const [tag, setTag] = useState([
    {
      name: "tech",
      value: "tech",
    },
    {
      name: "soft",
      value: "soft",
    },
  ]);

  const [Interviewer, setInterviewer] = useState({
    value: "",
  });

  const [q_id, setQuestion] = useState([{ q_id: "" }]);

  const interviewerTypes = [
    {
      name: "Male",
      value: "Male",
    },
    {
      name: "Female",
      value: "Female",
    },
  ];

  const [weightageValue, setWeightageValue] = useState(0);
  const [selectedQuestions, setSelectedQuestions] = useState([
    {
      Question: "",
      duration: "00:60",
    },
  ]);

  const onhandleFinalSubmit = (event, errors, values) => {
    event.preventDefault();
    console.log(q_id);
    const submit = {
      name,
      tag,
      questions: q_id,
      technical_weightage: weightageValue,
      soft_weightage: (100 - weightageValue).toString(),
      gender: Interviewer.value,
      customer_id: props.userId,
    };
    console.log("submit", submit);
    props.addInterview(submit, () => {
      history.push("/dashboard");
    });
  };

  const questionChange = (e, index) => {
    if (e.target.value !== "") {
      let temp = q_id;
      temp[index][e.target.name] = e.target.value;

      setQuestion([...temp]);
    }
  };

  const addQuestion = () => {
    setQuestion([...q_id, { q_id: "" }]);
  };

  const removeQuestion = (index) => {
    let temp = q_id;
    temp.splice(index, 1);

    setQuestion([...temp]);
  };

  const handleNameChange = (event) => {
    setName(event.target.value);
  };

  const handleTagChange = (event) => {
    setTag(event.target.value);
  };

  const handleSelectedQuestionsChange = (e, index) => {
    e.preventDefault();
    questionChange(e, index);
    const { name, value } = e.target;
    const listOfSelectedQuestions = [...selectedQuestions];
    console.log('value', value);
    listOfSelectedQuestions[index][name] = value;
    setSelectedQuestions(listOfSelectedQuestions);
  };

  const handleRemoveSelectedQuestions = (index) => {
    const list = [...selectedQuestions];
    list.splice(index, 1);
    setSelectedQuestions(list);
  };

  const handleInterviewerChange = (e) => {
    e.preventDefault();
    setInterviewer({
      value: e.target.value,
    });
  };

  return (
    <React.Fragment>
      <div className="page-content">
        <Container fluid={true}>
          <Breadcrumbs
            title="Interview Form"
            breadcrumbItems={breadcrumbItems}
          />
          <Row>
            <Col xl="12">
              <Card>
                <CardBody>
                  <AvForm className="needs-validation">
                    <Row>
                      <Col md="8">
                        <div className="mb-3">
                          <Label
                            className="form-label"
                            htmlFor="validationCustom01"
                          >
                            Name
                          </Label>
                          <AvField
                            name="Name"
                            placeholder="Enter Name"
                            type="text"
                            value={name}
                            onChange={handleNameChange}
                            errorMessage="Enter First Name"
                            className="form-control"
                            validate={{ required: { value: true } }}
                            id="validationCustom01"
                          />
                        </div>
                      </Col>
                      <Col md="4">
                        <div className="mb-3">
                          <Label
                            className="form-label"
                            htmlFor="validationCustom01"
                          >
                            Tag
                          </Label>
                          <FormGroup
                            row
                            className="mb-0"
                            value={tag.value}
                            onChange={handleTagChange}
                            validate={{ required: { value: true } }}
                            id="validationCustom01"
                          >
                            {" "}
                            <Col>
                              <select className="form-select">
                                <option defaultValue>Select tag</option>
                                <option value="tech">tech</option>
                                <option value="soft">soft</option>
                              </select>
                            </Col>
                          </FormGroup>
                        </div>
                      </Col>
                    </Row>
                    {q_id &&
                      q_id.map((questions, index) => (
                        <div className="mb-3">
                          <Row>
                            <Col md="4">
                              <Label
                                className="form-label"
                                htmlFor="validationCustom01"
                              >
                                Question
                              </Label>
                              <AvField
                                name="q_id"
                                placeholder="Enter question"
                                type="text"
                                className="form-control"
                                id="validationCustom01"
                                value={q_id[index].questions}
                                validate={{ required: { value: true } }}
                                onChange={(e) => questionChange(e, index)}
                              />
                            </Col>

                            <Col md="2">
                              <Label
                                className="form-label"
                                htmlFor="validationCustom01"
                              >
                                <br />
                              </Label>
                              <div className="mb-3">
                                <FormGroup>
                                  <Input
                                    Format="24"
                                    type="duration"
                                    name="duration"
                                    id="duration"
                                    value={questions.duration}
                                    validate={{ required: { value: true } }}
                                    onChange={(e) =>
                                      handleSelectedQuestionsChange(e, index)
                                    }
                                    placeholder="Enter Time"
                                    required
                                    maxLength="20"
                                  />
                                </FormGroup>
                              </div>
                            </Col>
                            <Col md="2">
                              <div className="mb-3">
                                <Label
                                  className="form-label"
                                  htmlFor="validationCustom01"
                                >
                                  <br />
                                </Label>
                                <FormGroup row className="mb-0">
                                  <Col>
                                    <Button
                                      color="primary"
                                      onClick={() => removeQuestion(index)}
                                    >
                                      Remove
                                    </Button>
                                  </Col>
                                </FormGroup>
                              </div>
                            </Col>
                            <Col md="2">
                              <div className="mb-2">
                                <Label
                                  className="form-label"
                                  htmlFor="validationCustom01"
                                >
                                  <br />
                                </Label>
                                <Col>
                                  <Button color="primary" onClick={addQuestion}>
                                    Add question
                                  </Button>
                                </Col>

                                {selectedQuestions.length == 1 ? null : (
                                  <Col md="1">
                                    <Button
                                      color="secondary"
                                      onClick={() =>
                                        handleRemoveSelectedQuestions(index)
                                      }
                                    >
                                      <FontAwesomeIcon icon={faTimes} />
                                    </Button>
                                  </Col>
                                )}
                              </div>
                            </Col>
                          </Row>
                        </div>
                      ))}

                    <Row>
                      <Col md="6">
                        <FormGroup>
                          <Label for="weightage">
                            Weightage of tech and soft skills
                          </Label>
                          <RangeSlider
                            className="form-control"
                            style={{ padding: 0 }}
                            tooltip="off"
                            value={weightageValue}
                            validate={{ required: { value: true } }}
                            id="validationCustom01"
                            errorMessage="Please provide weightage."
                            color="secondary"
                            onChange={(changeEvent) =>
                              setWeightageValue(changeEvent.target.value)
                            }
                          />
                          <Col sm="4">
                            <Label for="weightage">
                              {`Tech skills: ${weightageValue}%`}
                            </Label>
                            <Label for="weightage">
                              {`Soft skills: ${
                                weightageValue == 0 ? 0 : 100 - weightageValue
                              }%`}
                            </Label>
                          </Col>
                        </FormGroup>
                      </Col>
                    </Row>

                    <Row>
                      <Col md="6">
                        <div className="mb-3">
                          <FormGroup>
                            <Label
                              for="Interviewer"
                              className="form-label"
                              htmlFor="validationCustom01"
                            >
                              Interviewer
                            </Label>
                            <Input
                              type="select"
                              name="Interviewer"
                              id="Interviewer"
                              placeholder="Select Interviewer"
                              validate={{ required: { value: true } }}
                              value={Interviewer.value}
                              onChange={handleInterviewerChange}
                              required
                            >
                              <option selected disabled value="">
                                Select Interviewer Gender
                              </option>
                              {interviewerTypes &&
                              interviewerTypes.length > 0 ? (
                                interviewerTypes.map((interviewerType) => {
                                  return (
                                    <option
                                      value={interviewerType.value}
                                      key={interviewerType.value}
                                    >
                                      {interviewerType.name}
                                    </option>
                                  );
                                })
                              ) : (
                                <option disabled>
                                  No Interviewer Types Available
                                </option>
                              )}
                            </Input>
                          </FormGroup>
                        </div>
                      </Col>
                    </Row>
                    {/* <Link to="/dashboard"> */}
                      <Button
                        color="primary"
                        type="submit"
                        onClick={onhandleFinalSubmit}
                      >
                        Submit form
                      </Button>
                    {/* </Link> */}
                    <Link to="/dashboard">
                      <Button color="light" type="submit" className=" m-2">
                        Cancel
                      </Button>
                    </Link>
                  </AvForm>
                </CardBody>
              </Card>
            </Col>
          </Row>
        </Container>
      </div>
    </React.Fragment>
  );
};

const mapStateToProps = (state) => {
  console.log("state", state);
  return {
    userId: state.auth.user._id,
  };
};

const mapDispatchToProps = (dispatch) => {
  return {
    addInterview: (interviewObject, navigate) =>
      dispatch(interviewAdd(interviewObject, navigate)),
  };
};
export default connect(mapStateToProps, mapDispatchToProps)(AddInterview);

enter image description here



Solution 1:[1]

What is happening is that you are trying to access an item in the list using the index listOfSelectedQuestions[index] but the item doesn't exists.

What you can do is add an object to the index if it doesn't exists

if (listOfSelectedQuestions[index]) {
  // item exists, so only modify the property
  listOfSelectedQuestions[index][name] = value;
} else {
  // item doesn't exists, so add a new object entirely
  listOfSelectedQuestions[index] = {
    [name]: value
  }
}

Sources

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

Source: Stack Overflow

Solution Source
Solution 1 Vencovsky