Отправка сообщения (объекта) вместе с кодом статуса 404 (nodejs) - PullRequest
0 голосов
/ 24 января 2020

В настоящее время изучают NodeJS и Nuxt. Я надеюсь полностью понять цикл отправки объекта с клиента (интерфейс) на сервер (сервер) и затем получить ответ.

Например, я sh для отправки простой объект регистрации:

registerInfo: {
 username: '',
 email: '',
 password: ''
}

Этот объект отправляется с помощью действия Vuex:

async register (vuexContext, registerInfo) {
    try {
      const response = await axios.post('/register', registerInfo)
      console.log(response)
    } catch (err) {
      console.log(err)
    }
  }

Маршрутизатор (серверная часть работает в Express) получает запрос и вызывает соответствующая функция в файле контроллера:

router.post('/register', userController.register)

Функция файла контроллера выглядит следующим образом:

exports.register = async (req, res) => {
  const user = new User(req.body)

  try {
    await user.save()
    res.send({ user })
  } catch (err) {
    res.sendStatus(404).send(err)
  }
}

Я хотел показать все шаги для моего вопроса. Допустим, мы отправили пустой объект (в форме в интерфейсе не было введено никаких значений), а схема Mon goose (код для этого ниже) указывает, что все поля являются обязательными.

Когда mon goose собирается сохранить в базе данных, он проходит через схему и выдает ошибку (ie: «Требуется имя пользователя»), которая вызывает код блока catch. В котором я хочу отправить обратно клиенту статус 404. Но наряду с этим я также хочу отправить объект ошибки.

Однако вот что я вижу на интерфейсной консоли:

enter image description here

Не включает объект ошибки ( да, в коде выше я его не включал, однако .send (err) тоже не работает). Кроме того, я могу выполнить весь этот процесс в блоке try, проверив объект response на наличие свойства error . Но я чувствую, что это хакерство и не «дурак» Я младший разработчик, поэтому я могу быть совершенно неправ в этом отношении.

У кого-нибудь есть понимание моей проблемы?

Спасибо,


const UserSchema = new mongoose.Schema({
  username: {
    type: String,
    minlength: [3, 'Username must be at least 3 characters long'],
    required: [true, 'Username is required'],
    unique: [true, 'Username already exists.']
  },
  email: {
    type: String,
    required: [true, 'Email is required'],
    unique: [true, 'Email already exists.']
  },
  password: {
    type: String,
    minlength: [5, 'Password must be at least 5 characters long.'],
  }
})

Ответы [ 3 ]

3 голосов
/ 24 января 2020

res.sendStatus (statusCode)

Устанавливает код состояния HTTP ответа в значение statusCode и отправляет его строковое представление в качестве тела ответа.

 res.sendStatus(200) // equivalent to res.status(200).send('OK')
 res.sendStatus(403) // equivalent to res.status(403).send('Forbidden')
 res.sendStatus(404) // equivalent to res.status(404).send('Not Found') 
 res.sendStatus(500) // equivalent to res.status(500).send('Internal Server Error')

В вашем код, который вы отправляете таким образом, поэтому он пропустил ваш объект ошибки.

Итак, вы просто изменили это,

res.status(404).send(err)

Также я обновил js,

exports.register = async (req, res) =>
 { 
    const user = new User(req.body)
    user.save().then(()=> res.send({ user })).catch(err => res.sendStatus(404).send(err)):


 }
1 голос
/ 24 января 2020

Я предполагаю, что вы уже изменили res.sendStatus(404).send(err) с res.status(404).send(err);.

Теперь на стороне клиента вы можете прочитать данные ответа об ошибке с помощью err.response.data.

  // REGISTER
  async register(vuexContext, registerInfo) {
    try {
      const response = await axios.post("/moments/api/register", registerInfo);
      console.log(response);
    } catch (err) {
      if (err.response) {
        /* The request was made and the server responded with a status code that falls out of the range of 2xx*/
        console.log(err.response.data);
      } else {
        console.log("Error", err.message);
      }
    }
  }

Я также предлагаю следующий код на стороне сервера, это означает, что возвращать только 404, если имя ошибки ValidationError, и 500 для других случаев:

exports.register = async (req, res) => {
  const user = new User(req.body);

  try {
    await user.save();
    res.send({ user });
  } catch (err) {
    if (err.name === "ValidationError") {
      res.status(404).send(err);
    } else {
      console.log(err);
      res.status(500).send("Something went wrong");
    }
  }
};
1 голос
/ 24 января 2020

? Единственная причина , почему вы получаете ошибку 404, это потому, что если вы получаете какую-то ошибку от проверки, вы только res.sendStatus(404).

??‍? Измените это res.sendStatus(404); to res.status(400).send(error);

А теперь, ваш код будет выглядеть следующим образом : ?

exports.register = async (req, res) => {
  const user = new User(req.body)
  try {
    await user.save()
    res.send({ user })
  } catch (err) {
    // 400: badrequest
    res.status(400).send(err)
  }
}

? Обновлено: регистрация в веб-интерфейсе

Вы можете сначала попробовать этот код. Попробуйте распечатать ответ или ошибку:

register (vuexContext, formValue) {
    axios.post('/moments/api/register', formValue).then((response) => {
      console.log('Result: Succesfully to save data')
      console.log(response.data)
    }).catch((ex) => {
      console.log(`Result: Error result`)
      console.log(ex.response)
      console.log(ex.response.data)
    })
  }

? Обновлено (2): Изменить форму отправки

??‍? Вы можете изменить свой регистр формы: register.vue с указанным ниже кодом: ?

<form v-on:submit.prevent="register(registerInfo)" method="POST" >
  <input type="text" v-model="registerInfo.username" name="username" placeholder="Username">
  <input type="email" v-model="registerInfo.email" name="email" placeholder="Email">
  <input type="password" v-model="registerInfo.password" name="password" placeholder="Password">
  <input id="register" type="submit" placeholder="Register">
</form>

С помощью приведенной выше формы она никогда не будет перезагружаться при нажатии кнопки отправки.

Надеюсь, она поможет вам ? .

...