feat: add support for querystring in options object (#779)

In very few cases, some API uses the same key for both url and query params, such as the bulk method.
The client is not designed to handle such cases since accepts both url and query keys in the same object, and the url parameter will always take precedence.
This pr fixes this edge case by adding a `querystring` key in the options object.

Fixes: https://github.com/elastic/elasticsearch-js/pull/778

```js
client.bulk({
  index: 'index',
  type: '_doc',
  body: [...]
}, {
  querystring: {
    type: '_doc'
  }
}, console.log)
```
This commit is contained in:
Tomas Della Vedova
2019-03-15 18:09:44 +01:00
committed by GitHub
parent 851e839c70
commit c53c798899
261 changed files with 380 additions and 6 deletions

View File

@ -269,6 +269,32 @@ test('Pass unknown parameters as query parameters (and get a warning)', t => {
})
})
test('If the API uses the same key for both url and query parameter, the url should win', t => {
t.plan(2)
function handler (req, res) {
t.strictEqual(req.url, '/index/type/_bulk')
res.setHeader('Content-Type', 'application/json;utf=8')
res.end(JSON.stringify({ hello: 'world' }))
}
buildServer(handler, ({ port }, server) => {
const client = new Client({
node: `http://localhost:${port}`
})
// bulk has two `type` parameters
client.bulk({
index: 'index',
type: 'type',
body: []
}, (err, { body, warnings }) => {
t.error(err)
server.stop()
})
})
})
if (Number(process.version.split('.')[0].slice(1)) >= 8) {
require('./api-async')(test)
}

View File

@ -2030,3 +2030,80 @@ test('nodeFilter and nodeSelector', t => {
t.deepEqual(body, { hello: 'world' })
})
})
test('Should accept custom querystring in the optons object', t => {
t.test('Options object', t => {
t.plan(3)
function handler (req, res) {
t.strictEqual(req.url, '/hello?foo=bar')
res.setHeader('Content-Type', 'application/json;utf=8')
res.end(JSON.stringify({ hello: 'world' }))
}
buildServer(handler, ({ port }, server) => {
const pool = new ConnectionPool({ Connection })
pool.addConnection(`http://localhost:${port}`)
const transport = new Transport({
emit: () => {},
connectionPool: pool,
serializer: new Serializer(),
maxRetries: 3,
requestTimeout: 30000,
sniffInterval: false,
sniffOnStart: false
})
transport.request({
method: 'GET',
path: '/hello'
}, {
querystring: { foo: 'bar' }
}, (err, { body }) => {
t.error(err)
t.deepEqual(body, { hello: 'world' })
server.stop()
})
})
})
t.test('Options object and params', t => {
t.plan(3)
function handler (req, res) {
t.strictEqual(req.url, '/hello?baz=faz&foo=bar')
res.setHeader('Content-Type', 'application/json;utf=8')
res.end(JSON.stringify({ hello: 'world' }))
}
buildServer(handler, ({ port }, server) => {
const pool = new ConnectionPool({ Connection })
pool.addConnection(`http://localhost:${port}`)
const transport = new Transport({
emit: () => {},
connectionPool: pool,
serializer: new Serializer(),
maxRetries: 3,
requestTimeout: 30000,
sniffInterval: false,
sniffOnStart: false
})
transport.request({
method: 'GET',
path: '/hello',
querystring: { baz: 'faz' }
}, {
querystring: { foo: 'bar' }
}, (err, { body }) => {
t.error(err)
t.deepEqual(body, { hello: 'world' })
server.stop()
})
})
})
t.end()
})