mern — обновленные значения равны нулю в данных

#node.js #reactjs #mern

#node.js #reactjs #mern

Вопрос:

Я пытаюсь обновить записи. Запрос PUT в серверной части работает нормально, возвращая 200 и обновляя записи при тестировании на Postman, однако, когда я пытаюсь обновить запись во внешней части (react), я не получаю никаких ошибок, но обновленная запись не обновляется при отправке, и обновленные поля (заголовок и тело) равны нулю. Обновленные значения равны нулю, когда я console.log(data) во внешнем интерфейсе, поэтому они не отправляются на серверную часть, но они отображаются правильно в post . Почему обновленные значения находятся null внутри data ? Как я могу обновить сообщение новыми значениями вместо получения null?

data:
данные
post:
Публикация Обновленный код: Интерфейс

 const EditPost = ({match}) => {
  const [values, setValues] = useState({
    title: "",
    body: "",
    error: ""
  });
  
  const [post, setPost] = useState({});
  const { user, token } = isAuthenticated();
  const {
    title,
    body,
    error,
  } = values;


  const init = (id) => { 
      read(id).then(data => {
if (data.error) {
    setValues({...values, error: data.error})
} else {
    setValues({...values,
         title: data.title,
        body: data.body,
    }) 
    setPost({title: values.title, body: values.body})
     }
    })
}
 

useEffect(() => {
    const id = match.params.id;
  init(id);
}, []);

useEffect(() => {
  setPost({...values });
}, [values.title, values.body]);


  const handleChange = (name) => (event) => {
    setValues({ ...values, [name]: event.target.value });
  };

  const clickSubmit = (event) => {
    event.preventDefault();
    setValues({ ...values, error: "" });

    editPost(match.params.userId, match.params.id, token, post).then((data) => {
      if (data.error) {
        setValues({ ...values, error: data.error });
      } else {
        setValues({
          ...values,
          title: "",
          body: "",
          error: false,
        });      
      console.log(post)
      console.log(data)
      }
    });
  };

  const newPostForm = () => (
    <form onSubmit={clickSubmit}>
      <div>
        <input
          onChange={handleChange("title")} type="text"
          name="title"
          value={title}
        />
      </div>

      <div className="form-group">
        <textarea
          onChange={handleChange("body")}
          value={body} name="body"
        />
      </div>

      <button type="submit">Publish</button>
    </form>
  );
  const showError = () => (
    <div
      style={{ display: error ? "" : "none" }}>
      {error}
    </div>
  );

  return (
        <div>  
          {showError()}
          {newPostForm()}
        </div>
  );
};

export default EditPost;
  
 export const editPost = (userId, id, token, post) => {
    return fetch(`${API}/${userId}/${id}/edit`, {
        method: 'PUT',
        headers: {
            Accept: 'application/json',
            Authorization: `Bearer ${token}`
        },
        body: JSON.stringify(post)
    })
        .then(response => {
            return response.json();
            
        })
        .catch(err => console.log(err));
};
  

postsByUser.js

  <Link className="mypost_btn edit_btn" to={`/${_id}/${post._id}/edit`}>
     Edit
 </Link>
  

Внутренний код

 exports.edit = (req, res) => {
  if (!ObjectID.isValid(req.params.id))
        return res.status(400).send(`ID is not valid: ${req.params.id}`)

  const {title, body} = req.body

  const updatedPost = {title, body }

  Post.findByIdAndUpdate(req.params.id, {
    $set: updatedPost
  }, {new:true}, (error, data) => {
    if (error) {
      return error
    } else {
      res.send(data)
      console.log(data)
    }
  })
}
  

Комментарии:

1. данные поступают из read, так что в этом ваша проблема, но у нас нет внутреннего кода, в котором должна быть проблема, потому что он не возвращает данные.

2. Хорошо, спасибо, я добавил код! @7iiBob

3. Когда вы проверяете свое состояние, видите ли вы значения?

4. Можете ли вы подтвердить, что console.log() inside of exports.edit распечатывает данные, которые отправляются в объект ответа?

5. @Rahni, не могли бы вы, пожалуйста, проверить, что вы получаете в ответ? Я полагаю, что сам ответ находится в формате json, нет необходимости преобразовывать его в json.

Ответ №1:

Ваша проблема заключается вот в чем:

 editPost(match.params.userId, match.params.id, token, post)
  

post не определено.

Поскольку post не определено, данные не передаются. Следовательно, title и body равно null . Что вам нужно будет сделать, это, исходя из того, что я вижу в вашем коде, определить переменную состояния с именем post . Я думаю, вы намеревались это сделать:

 const [post, setPost] = useState({values.title, values.body});
  

Затем убедитесь, что ваш post обновляется всякий раз, когда вы values изменяете, используя useEffect() ,

 useEffect(() => {
   setPost({...values });
}, [values.title, value.body]);
  

Таким образом, к тому времени, когда вы вызываете свой editPost() http-put-метод, у post есть value . И это должно сработать.

Комментарии:

1. Благодарю вас за ваш ответ. Это очень помогло, и теперь я получаю значения для заголовка и тела, post хотя data для обновленных значений все еще возвращается значение null. По сути, post содержит только значения в состоянии (заголовок, тело и ошибка), тогда как data содержит всю запись целиком.

2. По крайней мере, мы приближаемся… Не могли бы вы, пожалуйста, console.log(updatedPost ) зайти на свой сервер и посмотреть, действительно ли на стороне сервера получено title и body ? Понятно, что они устанавливаются и отправляются с интерфейсной стороны, но поведение показывает, что они не сохраняются, если они возвращают null. Пожалуйста, войдите в консоль и дайте мне знать о том, что происходит?

3. У меня есть console.log(updatedPost) и значения не определены. Я получаю { title: undefined, body: undefined }} @MosiaThabo

4. Тогда они не передаются в серверную часть, или они неправильно привязываются. Все, что вам нужно сделать, это убедиться, что они направляются на серверную часть. Я думаю, что на данный момент это единственная проблема.

5. Определенно, эти небольшие проблемы / ошибки являются причиной того, что работа над функцией занимает намного больше времени, чем в противном случае, но я так рад, что наконец-то заработала эта функция редактирования записи. Переходим к следующей проблеме, которую нужно решить 🙂 Спасибо! @Мосиатабо

Ответ №2:

в EditPost.js editPost(match.params.userId, match.params.id, token).then((data) => { здесь вам не хватает 4-го аргумента, который является «публикацией», которую вы сами отправляете для обновления

Комментарии:

1. Спасибо за ваш ответ. Я добавил post в качестве аргумента, но все равно, когда я console.log(data) получаю null для полей title и body. Я попытался установить состояние для post, но, похоже, у меня не получается заставить его работать. @AlyAbdElRahman

2. Я бы утешил. зарегистрируйте идентификатор на серверной части внутри readById и проверьте терминал и убедитесь, что идентификатор проходит через него. Вы уверены, что запись создается с самого начала?

3. Да, сообщение определенно создается, и readById также работает. У меня есть console.log(id) в readById и edit , и они оба правильные. @7iiBob

4. @Rahni не могли бы вы, пожалуйста, обновить код в EditPost.js editPost , чтобы мы могли видеть, как вы отправляете данные post?