@Pavel_Tkachenko
Да, я преступник. Моё преступление — любопытство

Как получить имя параметра маршрута Express?

Каким образом можно получить имя параметра в маршруте Express?
Имею к примеру маршрут
'/user/:userId'
При переходе получаю динамический адрес/user/5af2fe6cc7a7631ae040db43
Хочу сделать промежуточный обработчик который будет выбирать информацию о маршруте из БД,
Найти в БД динамический адрес не получится без преобразования 5af2fe6cc7a7631ae040db43 в /:и поиск соответствия/user/:
Такой скрипт я сделал, но мне интересно есть ли способ полегче, тем более, что скрипт работает только с 1 параметром, то есть к примеру /user/:username/:userId он пока не сможет обработать (надо допилить).
Пример кода для наглядности:
// Moongose
var Routes = mongoose.model('Routes', RoutesSchema);

app.use((req, res, next) => {
    //Получаем информацию о маршруте из бд
    Routes.find({'path' : req.originalUrl}, (err, pageInfo) => {
        // Если документ не найден
        if(pageInfo == null) {
            var search = req.originalUrl.split('/');
            search.splice(-1,1,':');
            search = search.join('/');
            // serach =  /user/:
            Routes.findOne({'path' : {$regex: search}}, function(err, pageInfo) {
                // Устанавливаем локальные переменные ответа
                res.locals.title = pageInfo.title;
                res.locals.description = pageInfo.description;
                next()
            })
        }
        // Если все ок
        else {
            // Устанавливаем локальные переменные ответа
            res.locals.title = pageInfo.title
            res.locals.description= pageInfo.description
            next()
       }
    })
})

Заранее благодарен
  • Вопрос задан
  • 200 просмотров
Пригласить эксперта
Ответы на вопрос 2
@rustler2000
погромист сикраш
Кароче вопрос простой без балды.
Вот кусок кода стыриный с кейса в expressjs и их доки.

Суть, что перед запуском сервера, проходит по обработчикам и вставляет передними трамплин.

const express = require('express')
const app = express()

app.get('/path/:id', function(req, res, next) {
    res.send(`${this.method} ${this.path}`)
})

function print (path, layer) {
  if (layer.route) {
    layer.route.stack.forEach(print.bind(null, path.concat(split(layer.route.path))))
  } else if (layer.name === 'router' && layer.handle.stack) {
    layer.handle.stack.forEach(print.bind(null, path.concat(split(layer.regexp))))
  } else if (layer.method) {
    console.log('%s /%s',
      layer.method.toUpperCase(),
      path.concat(split(layer.regexp)).filter(Boolean).join('/'))
      
    // 
    // Аттачим хэндлеру this :D
    // 
    const m = layer.method.toUpperCase()
    const p = path.concat(split(layer.regexp)).filter(Boolean).join('/')
    const fn = layer.handle
    layer.handle = function trampoline() {
        const self = {
            method: m,
            path: p
        }
        
        fn.apply(self, arguments)
    }
  }
}

function split (thing) {
  if (typeof thing === 'string') {
    return thing.split('/')
  } else if (thing.fast_slash) {
    return ''
  } else {
    var match = thing.toString()
      .replace('\\/?', '')
      .replace('(?=\\/|$)', '$')
      .match(/^\/\^((?:\\[.*+?^${}()|[\]\\\/]|[^.*+?^${}()|[\]\\\/])*)\$\//)
    return match
      ? match[1].replace(/\\(.)/g, '$1').split('/')
      : '<complex:' + thing.toString() + '>'
  }
}
app._router.stack.forEach(print.bind(null, []))

app.listen(3000, () => console.log('Example app listening on port 3000!'))
Ответ написан
@Pavel_Tkachenko Автор вопроса
Да, я преступник. Моё преступление — любопытство
Не получится получится получить имя параметра запроса, так как промежуточный обработчик выполняется перед обработкой самого маршрута и не в курсе что 5af2fe6cc7a7631ae040db43 - это параметр запроса.
Ответ написан
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы