Body parser использует промежуточное ПО bodyParser из другого промежуточного ПО - PullRequest
0 голосов
/ 17 января 2019

Итак, я работаю над этим экспресс-приложением, в котором все маршруты имеют ограниченный размер тела, кроме случаев, когда вы являетесь администратором, поскольку администратору нужен неограниченный размер тела для нескольких маршрутов. У меня есть программное обеспечение limitBodySize, и я использую его следующим образом: app.use(middleware.limitBodySize)

Но, в конце концов, мое тело не анализируется, и все не определено.

limitBodySize: (req, res, next) => {
  let admin = true; // removed extra steps for simplicity

  if (admin) {
    bodyParser.urlencoded({ extended: false })(req, res, () => {
      console.log(req.body) // logs undefined
      bodyParser.json()(req, res, () => {
        console.log(req.body) // logs undefined
        next(); // in next route, console.log(req.body) logs undefined
      });
    });
  } else {
    bodyParser.urlencoded({ extended: false, limit: '1kb' })(req, res, () => {
      bodyParser.json({ limit: '1kb' })(req, res, () => {
        next();
      });
    });
  }
}

Как решить эту проблему, используя только одно промежуточное ПО, не передавая промежуточное ПО bodyParser на каждый маршрут или маршрутизатор отдельно.

1 Ответ

0 голосов
/ 17 января 2019

Прежде всего, вы должны сгенерировать промежуточное программное обеспечение bodyParser вне своего пользовательского условного промежуточного программного обеспечения, поскольку оно предназначено для многократного использования.

Вы также не проверяете ошибки; возможно, ваше промежуточное ПО bodyParser выдает ошибку анонимным обратным вызовам, которые вы передали им в качестве параметра next, поэтому обрабатывайте ошибки правильно. Один из самых простых способов сделать это состоит в том, чтобы пообещать каждое промежуточное ПО с помощью модуля util, так как вы все равно уже связываете их.

Я подозреваю, что вашим телом запроса может быть JSON, а промежуточное ПО urlencoded пытается его проанализировать безуспешно. На данный момент bodyParser использует поток тела, поэтому промежуточное программное обеспечение json, вероятно, также выйдет из строя. Поскольку вы игнорируете обе ошибки, вы не будете точно знать, какое будет следующее исправление, пока не попробуете это:

const { promisify } = require('util')
const json = promisify(bodyParser.json())
const limitedJson = promisify(bodyParser.json({ limit: '1kb' }))
const urlencoded = promisify(bodyParser.urlencoded({ extended: false }))
const limitedUrlencoded = promisify(bodyParser.urlencoded({ extended: false, limit: '1kb' }))

...

limitBodySize: (req, res, next) => {
  ...

  if (admin) {
    urlencoded(req, res).then(
      () => json(req, res)
    ).then(
      () => next(),
      next
    )
  } else {
    limitedUrlencoded(req, res).then(
      () => limitedJson(req, res)
    ).then(
      () => next(),
      next
    )
  }
}

Это передаст любые ошибки в экспресс-инфраструктуру, используя параметр onRejected .then()

Используя синтаксис async и await в ECMAScript 2017, вы можете немного упростить чтение:

limitBodySize: async (req, res, next) => {
  ...

  try {
    if (admin) {
      await urlencoded(req, res)
      await json(req, res)
    } else {
      await limitedUrlencoded(req, res)
      await limitedJson(req, res)
    }

    next()
  } catch (error) {
    // if error occurs here, you probably need to figure out what your next issue is
    next(error)
  }
}
...