Невозможно установить заголовки после их отправки клиенту - записи, сохраненные в MongoDb - Express.Js - PullRequest
0 голосов
/ 07 мая 2019

Я знаю, что этот вопрос часто задают, но я не могу сказать, куда я отправляю несколько заголовков. Данные сохраняются в базе данных, а затем происходит сбой. Я довольно новичок в Node / Express и думаю, что мне здесь не хватает чего-то фундаментального.

Я попытался прочитать то, что смог найти в stackoverflow, и выяснил, почему я получаю эту ошибку, потому что она отправляет несколько запросов заголовка. Попытался обновить код с небольшими изменениями, но пока ничего не получалось.

Спасибо за помощь.

Контроллер панели приборов -

exports.getGymOwnerMembersAdd = (req, res, next) => {
    let message = req.flash('error');
    if(message.length > 0) {
        message = message[0];
    } else {
        message = null;
    }
    const oldInput = {
      ...
    };

    Membership
        .find()
        .then(memberships => {
            res.render('gym-owner/members-add', {
                memberships: memberships,
                oldInput: oldInput,
                errorMessage: message,
                pageTitle: 'Add Members',
                path: '/gym-owner-dashboard/members-add',
                validationErrors: []
            });
        })
        .catch(err => {
            console.log(err);
        });
}

exports.postGymOwnerMembersAdd = (req, res, next) => {
    const membershipId = req.body.membershipLevel;
    const errors = validationResult(req);
    let message = req.flash('error');

    if(message.length > 0) {
        message = message[0];
    } else {
        message = null;
    }

    if(!errors.isEmpty()) {
        Membership
            .find()
            .then(memberships => {
                return res.status(422).render('gym-owner/members-add', {
                    pageTitle: 'Add Members',
                    path: '/gym-owner-dashboard/members-add',
                    errorMessage: errors.array()[0].msg,
                    message: message,
                    memberships: memberships,
                    oldInput: { 
                        ...
                    },
                    validationErrors: errors.array()
                });
            })
            .catch(next);
    }

    bcrypt
        .hash(password, 12)
        .then(hashedPassword => {
            const user = new User({
                ...
            });
            return user.save();
        })
        .then(result => {
            res.redirect('/gym-owner-dashboard/members');
        })
        .catch(err=> {
            console.log(err);
        });
}

Маршруты и проверка панели управления -

router.get('/gym-owner-dashboard/members-add', isAuth, isGymOwner, dashboardController.getGymOwnerMembersAdd);
router.post(
    '/gym-owner-dashboard/members-add',
    isAuth, isGymOwner, 
    [
        check('name')
            .isAlpha().withMessage('Names can only contain letters.')
            .isLength({ min: 2 }).withMessage('Please enter a valid name')
            .trim(),
        check('email')
            .isEmail().withMessage('Please enter a valid email.')
            .custom((value, { req }) => {
                return User.findOne({
                    email: value
                }).then(userDoc => {
                    console.log('Made it here!');
                    if(userDoc) {
                        return Promise.reject('E-mail already exists, please pick a different one.');
                    };
                });
            })
            .normalizeEmail(),
        ...
        check(
            'password',
            'Please enter a password at least 5 characters.'
        )
            .isLength({ min: 5 })
            .trim(),
        check('confirmPassword')
            .trim()
            .custom((value, { req }) => {
                if(value !== req.body.password) {
                    throw new Error('Passwords have to match!');
                }
                return true;
            })
    ], 
    dashboardController.postGymOwnerMembersAdd
);

Ожидаемые результаты Создайте нового пользователя при прохождении проверки.

Фактические результаты Новый пользователь создан и сохранен в Mongodb. Пользователь перенаправляется обратно на страницу создания пользователя с ошибкой, что пользователь не определен. Сервер аварийно завершает работу с ошибкой «Ошибка [ERR_HTTP_HEADERS_SENT]: невозможно установить заголовки после их отправки клиенту»

1 Ответ

1 голос
/ 07 мая 2019

Насколько я понимаю, у вас есть ошибка в "postGymOwnerMembersAdd".

    if(!errors.isEmpty()) {
        Membership
            .find()
            .then(memberships => {
                return res.status(422).render('gym-owner/members-add', { // this return refers to cb but not to middleware
                    pageTitle: 'Add Members',
                    path: '/gym-owner-dashboard/members-add',
                    errorMessage: errors.array()[0].msg,
                    message: message,
                    memberships: memberships,
                    oldInput: { 
                        ...
                    },
                    validationErrors: errors.array()
                });
            })
            .catch(next);
    }

    bcrypt
        .hash(password, 12)
        .then(hashedPassword => {
            const user = new User({
                ...
            });
            return user.save();
        })
        .then(result => {
            res.redirect('/gym-owner-dashboard/members');
        })
        .catch(err=> {
            console.log(err);
        });

Таким образом, и "return res.status (422) .render ()" и "res.redirect ('/ gym)-owner-dashboard / members ') ", и эта ошибка запуска (заголовок устанавливается после их отправки).
Я имею в виду два решения проблемы Первый: используйте async / await

exports.postGymOwnerMembersAdd = async (req, res, next) => {
  const membershipId = req.body.membershipLevel;
  const errors = validationResult(req);
  let message = req.flash('error');

  if(message.length > 0) {
    message = message[0];
  } else {
    message = null;
  }

  if(!errors.isEmpty()) {
    try {
      const memberships = await Membership.find();
      return res.status(422).render('gym-owner/members-add', {
        pageTitle: 'Add Members',
        path: '/gym-owner-dashboard/members-add',
        errorMessage: errors.array()[0].msg,
        message: message,
        memberships: memberships,
        oldInput: {
          ...
        },
        validationErrors: errors.array()
      };
    } catch (err) {
      next(err);
    }
  }

  const hashedPassword = await bcrypt.hash(password, 12);
  const user = new User({
    ...
  });
  await user.save();
  return res.redirect('/gym-owner-dashboard/members');
};

Второй: используйте else

exports.postGymOwnerMembersAdd = (req, res, next) => {
  const membershipId = req.body.membershipLevel;
  const errors = validationResult(req);
  let message = req.flash('error');

  if(message.length > 0) {
    message = message[0];
  } else {
    message = null;
  }

  if(!errors.isEmpty()) {
    Membership
      .find()
      .then(memberships => {
        return res.status(422).render('gym-owner/members-add', {
          pageTitle: 'Add Members',
          path: '/gym-owner-dashboard/members-add',
          errorMessage: errors.array()[0].msg,
          message: message,
          memberships: memberships,
          oldInput: {
            ...
          },
          validationErrors: errors.array()
        });
      })
      .catch(next);
  } else {
    bcrypt
      .hash(password, 12)
      .then(hashedPassword => {
        const user = new User({
          ...
        });
        return user.save();
      })
      .then(result => {
        res.redirect('/gym-owner-dashboard/members');
      })
      .catch(err=> {
        console.log(err);
      });
  }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...