Как получить доступ к параметрам GET после «?» в экспрессе?

528

Я знаю, как получить параметры для таких запросов:

app.get('/sample/:id', routes.sample);

В этом случае я могу использовать req.params.idдля получения параметра (например, 2в /sample/2).

Тем не менее, для URL, как /sample/2?color=red, как я могу получить доступ к переменной color?

Я пытался, req.params.colorно это не сработало.

Hanfei Sun
источник

Ответы:

777

Итак, после проверки экспресс-ссылки , я обнаружил, req.query.colorчто вернет мне искомое значение.

req.params относится к элементам с ':' в URL, а req.query относится к элементам, связанным с '?'

Пример:

GET /something?color1=red&color2=blue

Затем в экспресс, обработчик:

app.get('/something', (req, res) => {
    req.query.color1 === 'red'  // true
    req.query.color2 === 'blue' // true
})
Hanfei Sun
источник
Не могли бы вы сказать мне, как проверить «идентификатор»?
Ананд Радж
1
@AnandRaj: что вы имеете в виду: как проверить «id»? Какую проверку вы хотите? Кстати, вы можете получить значение idв вашей функции , как это: var sampleId = req.params.id;.
Йохем Шуленклоппер
4
Используйте req.params.whateverв последних версиях.
adelriosantiago
3
Имейте в виду, что req.paramsотличается от req.query! expressjs.com/en/api.html#req.params expressjs.com/en/api.html#req.query @adelriosantiago
caesarsol
81

Используйте req.query для получения значения в параметре строки запроса на маршруте. Обратитесь к req.query . Скажем, если в маршруте http: // localhost: 3000 /? Name = satyam вы хотите получить значение для параметра имени, то ваш обработчик маршрута 'Get' будет выглядеть так: -

app.get('/', function(req, res){
    console.log(req.query.name);
    res.send('Response send to client::'+req.query.name);

});
сатьям кумар
источник
возможно некоторая информация о строке запроса, чтобы получить полный ответ
Schuere
67

Обновление: req.param() теперь устарело, поэтому в дальнейшем не используйте этот ответ.


Ваш ответ является предпочтительным способом сделать это, однако я подумал, что могу также указать, что вы также можете получить доступ к параметрам url, post и route req.param(parameterName, defaultValue).

В твоем случае:

var color = req.param('color');

Из экспресс-гида:

поиск выполняется в следующем порядке:

  • req.params
  • req.body
  • req.query

Обратите внимание, что в руководстве указано следующее:

Прямой доступ к req.body, req.params и req.query должен быть предпочтительным для ясности - если вы действительно не принимаете входные данные от каждого объекта.

Однако на практике я обнаружил, req.param()что достаточно ясен и облегчает определенные виды рефакторинга.

Zugwalt
источник
53

Строка запроса и параметры разные.

Вы должны использовать оба в одном URL маршрутизации

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

app.get('/sample/:id', function(req, res) {

 var id = req.params.id; //or use req.param('id')

  ................

});

Получите ссылку для прохождения вашего второго сегмента, ваш пример id: http: // localhost: port / sample / 123

Если вы столкнулись с проблемой, используйте переменную Passing в качестве строки запроса, используя '?' оператор

  app.get('/sample', function(req, res) {

     var id = req.query.id; 

      ................

    });

Получить ссылку, как этот пример: http: // localhost: port / sample? Id = 123

Оба в одном примере

app.get('/sample/:id', function(req, res) {

 var id = req.params.id; //or use req.param('id')
 var id2 = req.query.id; 
  ................

});

Пример получения ссылки: http: // localhost: port / sample / 123? Id = 123

Раджа Рама Мохан Тавалам
источник
2
Спасибо, этот ответ был очень полезным!
Бруно Таварес
44

@ Zugwait ответ правильный. req.param()устарел. Вы должны использовать req.params, req.queryили req.body.

Но просто чтобы было понятнее:

req.paramsбудут заполнены только значениями маршрута. То есть, если у вас есть такой маршрут /users/:id, вы можете получить доступ idлибо в, req.params.idлибо req.params['id'].

req.queryи req.bodyбудут заполнены всеми параметрами, независимо от того, находятся ли они в маршруте. Конечно, параметры в строке запроса будут доступны в, req.queryа параметры в теле сообщения будут доступны в req.body.

Поэтому, отвечая на ваши вопросы, colorкоторых нет в маршруте, вы сможете получить его, используя req.query.colorили req.query['color'].

Андре Пена
источник
17

Экспресс-руководство говорит, что вы должны использовать req.query для доступа к QueryString.

// Requesting /display/post?size=small
app.get('/display/post', function(req, res, next) {

  var isSmall = req.query.size === 'small'; // > true
  // ...

});
Ян Биаси
источник
7
const express = require('express')
const bodyParser = require('body-parser')
const { usersNdJobs, userByJob, addUser , addUserToCompany } = require ('./db/db.js')

const app = express()
app.set('view engine', 'pug')
app.use(express.static('public'))
app.use(bodyParser.urlencoded({ extended: false }))
app.use(bodyParser.json())

app.get('/', (req, res) => {
  usersNdJobs()
    .then((users) => {
      res.render('users', { users })
    })
    .catch(console.error)
})

app.get('/api/company/users', (req, res) => {
  const companyname = req.query.companyName
  console.log(companyname)
  userByJob(companyname)
    .then((users) => {
      res.render('job', { users })
    }).catch(console.error)
})

app.post('/api/users/add', (req, res) => {
  const userName = req.body.userName
  const jobName = req.body.jobName
  console.log("user name = "+userName+", job name : "+jobName)
  addUser(userName, jobName)
    .then((result) => {
      res.status(200).json(result)
    })
    .catch((error) => {
      res.status(404).json({ 'message': error.toString() })
    })
})
app.post('/users/add', (request, response) => {
  const { userName, job } = request.body
  addTeam(userName, job)
  .then((user) => {
    response.status(200).json({
      "userName": user.name,
      "city": user.job
    })
  .catch((err) => {
    request.status(400).json({"message": err})
  })
})

app.post('/api/user/company/add', (req, res) => {
  const userName = req.body.userName
  const companyName = req.body.companyName
  console.log(userName, companyName)
  addUserToCompany(userName, companyName)
  .then((result) => {
    res.json(result)
  })
  .catch(console.error)
})

app.get('/api/company/user', (req, res) => {
 const companyname = req.query.companyName
 console.log(companyname)
 userByJob(companyname)
 .then((users) => {
   res.render('jobs', { users })
 })
})

app.listen(3000, () =>
  console.log('Example app listening on port 3000!')
)
сема
источник
7
Спасибо за этот фрагмент кода, который может оказать некоторую ограниченную, немедленную помощь. Надлежащее объяснение было бы значительно улучшить свою долгосрочную ценность , показывая , почему это хорошее решение проблемы, и сделает его более полезным для читателей будущих с другими подобными вопросами. Пожалуйста, измените свой ответ, чтобы добавить некоторые объяснения, в том числе предположения, которые вы сделали.
iBug
2

Хорошая техника, которую я начал использовать с некоторыми из моих приложений в Express, - это создание объекта, который объединяет поля запроса, params и body объекта запроса Express.

//./express-data.js
const _ = require("lodash");

class ExpressData {

    /*
    * @param {Object} req - express request object
    */
    constructor (req) {

        //Merge all data passed by the client in the request
        this.props = _.merge(req.body, req.params, req.query);
     }

}

module.exports = ExpressData;

Затем в теле контроллера или где-либо еще в области цепочки экспресс-запросов вы можете использовать что-то вроде следующего:

//./some-controller.js

const ExpressData = require("./express-data.js");
const router = require("express").Router();


router.get("/:some_id", (req, res) => {

    let props = new ExpressData(req).props;

    //Given the request "/592363122?foo=bar&hello=world"
    //the below would log out 
    // {
    //   some_id: 592363122,
    //   foo: 'bar',
    //   hello: 'world'
    // }
    console.log(props);

    return res.json(props);
});

Это делает удобным и удобным просто "вникать" во все "пользовательские данные", которые пользователь, возможно, отправил со своим запросом.

Запись

Почему поле "реквизит"? Поскольку это был сокращенный фрагмент, я использую эту технику в ряде своих API, я также храню данные аутентификации / авторизации для этого объекта, пример ниже.

/*
 * @param {Object} req - Request response object
*/
class ExpressData {

    /*
    * @param {Object} req - express request object
    */
    constructor (req) {

        //Merge all data passed by the client in the request
        this.props = _.merge(req.body, req.params, req.query);

        //Store reference to the user
        this.user = req.user || null;

        //API connected devices (Mobile app..) will send x-client header with requests, web context is implied.
        //This is used to determine how the user is connecting to the API 
        this.client = (req.headers) ? (req.headers["x-client"] || (req.client || "web")) : "web";
    }
} 
Ли Бриндли
источник
1
Вероятно, это плохая идея, потому что это затрудняет поддержание ваших конечных точек. Вы больше не знаете, какой метод клиенты будут использовать для передачи параметров.
sdgfsdh
Это на самом деле одно из главных преимуществ такого подхода, если честно, не нужно знать, откуда берутся поля. Вышеуказанный класс ExpressData действует как мост, позволяющий вам модулировать бизнес-логику, отодвигая ее от маршрутов экспресс-контроллера, т.е. вы не встраиваете 'req.query', 'req.body' в свой код, это также делает Ваш бизнес-код легко тестируется, полностью вне экспресс.
Ли Бриндли