From 6d605ec30afc4ac4945cff5fe9e051223b992855 Mon Sep 17 00:00:00 2001 From: Spencer Date: Tue, 20 Jun 2017 21:35:33 -0400 Subject: [PATCH] [5.5] [api/indexPatterns/fields] convert all es errors to Boom errors (#12435) --- .../service/lib/__tests__/es_api.js | 24 ++++++------- .../index_patterns/service/lib/errors.js | 6 ++-- .../index_patterns/service/lib/es_api.js | 6 ++-- .../apis/index_patterns/es_errors/errors.js | 34 ++++++++++++------- 4 files changed, 41 insertions(+), 29 deletions(-) diff --git a/src/server/index_patterns/service/lib/__tests__/es_api.js b/src/server/index_patterns/service/lib/__tests__/es_api.js index 9692b6e44c35c..438a5afbe1005 100644 --- a/src/server/index_patterns/service/lib/__tests__/es_api.js +++ b/src/server/index_patterns/service/lib/__tests__/es_api.js @@ -1,8 +1,8 @@ import sinon from 'sinon'; import expect from 'expect.js'; -import { convertEsIndexNotFoundError } from '../errors'; -import * as convertEsIndexNotFoundErrorNS from '../errors'; +import { convertEsError } from '../errors'; +import * as convertEsErrorNS from '../errors'; import { callIndexAliasApi, callFieldCapsApi } from '../es_api'; @@ -45,21 +45,21 @@ describe('server/index_patterns/service/lib/es_api', () => { expect(passedOpts).to.have.property('allowNoIndices', false); }); - it('handles errors with convertEsIndexNotFoundError()', async () => { + it('handles errors with convertEsError()', async () => { const indices = []; const esError = new Error('esError'); const convertedError = new Error('convertedError'); - sandbox.stub(convertEsIndexNotFoundErrorNS, 'convertEsIndexNotFoundError', () => { throw convertedError; }); + sandbox.stub(convertEsErrorNS, 'convertEsError', () => { throw convertedError; }); const callCluster = sinon.spy(async () => { throw esError; }); try { await callIndexAliasApi(callCluster, indices); throw new Error('expected callIndexAliasApi() to throw'); } catch (error) { expect(error).to.be(convertedError); - sinon.assert.calledOnce(convertEsIndexNotFoundError); - expect(convertEsIndexNotFoundError.args[0][0]).to.be(indices); - expect(convertEsIndexNotFoundError.args[0][1]).to.be(esError); + sinon.assert.calledOnce(convertEsError); + expect(convertEsError.args[0][0]).to.be(indices); + expect(convertEsError.args[0][1]).to.be(esError); } }); }); @@ -103,21 +103,21 @@ describe('server/index_patterns/service/lib/es_api', () => { expect(passedOpts).to.have.property('allowNoIndices', false); }); - it('handles errors with convertEsIndexNotFoundError()', async () => { + it('handles errors with convertEsError()', async () => { const indices = []; const esError = new Error('esError'); const convertedError = new Error('convertedError'); - sandbox.stub(convertEsIndexNotFoundErrorNS, 'convertEsIndexNotFoundError', () => { throw convertedError; }); + sandbox.stub(convertEsErrorNS, 'convertEsError', () => { throw convertedError; }); const callCluster = sinon.spy(async () => { throw esError; }); try { await callFieldCapsApi(callCluster, indices); throw new Error('expected callFieldCapsApi() to throw'); } catch (error) { expect(error).to.be(convertedError); - sinon.assert.calledOnce(convertEsIndexNotFoundError); - expect(convertEsIndexNotFoundError.args[0][0]).to.be(indices); - expect(convertEsIndexNotFoundError.args[0][1]).to.be(esError); + sinon.assert.calledOnce(convertEsError); + expect(convertEsError.args[0][0]).to.be(indices); + expect(convertEsError.args[0][1]).to.be(esError); } }); }); diff --git a/src/server/index_patterns/service/lib/errors.js b/src/server/index_patterns/service/lib/errors.js index c5805401ee81a..a2ef9f1cc396d 100644 --- a/src/server/index_patterns/service/lib/errors.js +++ b/src/server/index_patterns/service/lib/errors.js @@ -42,10 +42,12 @@ export function isNoMatchingIndicesError(err) { * @param {[type]} indices [description] * @return {[type]} [description] */ -export function convertEsIndexNotFoundError(indices, error) { +export function convertEsError(indices, error) { if (isEsIndexNotFoundError(error)) { return createNoMatchingIndicesError(indices); } - return error; + const statusCode = error.statusCode; + const message = error.body ? error.body.error : undefined; + return Boom.wrap(error, statusCode, message); } diff --git a/src/server/index_patterns/service/lib/es_api.js b/src/server/index_patterns/service/lib/es_api.js index c0445812d757b..b52740e3e5b29 100644 --- a/src/server/index_patterns/service/lib/es_api.js +++ b/src/server/index_patterns/service/lib/es_api.js @@ -1,4 +1,4 @@ -import { convertEsIndexNotFoundError } from './errors'; +import { convertEsError } from './errors'; /** * Call the index.getAlias API for a list of indices. @@ -22,7 +22,7 @@ export async function callIndexAliasApi(callCluster, indices) { allowNoIndices: false }); } catch (error) { - throw convertEsIndexNotFoundError(indices, error); + throw convertEsError(indices, error); } } @@ -46,6 +46,6 @@ export async function callFieldCapsApi(callCluster, indices) { allowNoIndices: false }); } catch (error) { - throw convertEsIndexNotFoundError(indices, error); + throw convertEsError(indices, error); } } diff --git a/test/api_integration/apis/index_patterns/es_errors/errors.js b/test/api_integration/apis/index_patterns/es_errors/errors.js index 6c82cd50a38e5..ed4b0716f23a2 100644 --- a/test/api_integration/apis/index_patterns/es_errors/errors.js +++ b/test/api_integration/apis/index_patterns/es_errors/errors.js @@ -1,10 +1,11 @@ import expect from 'expect.js'; +import { errors as esErrors } from 'elasticsearch'; import { isEsIndexNotFoundError, createNoMatchingIndicesError, isNoMatchingIndicesError, - convertEsIndexNotFoundError + convertEsError } from '../../../../../src/server/index_patterns/service/lib/errors'; import { @@ -76,25 +77,34 @@ export default function ({ getService }) { }); }); - describe('convertEsIndexNotFoundError()', () => { + describe('convertEsError()', () => { const indices = ['foo', 'bar']; it('converts indexNotFoundErrors into NoMatchingIndices errors', async () => { - const converted = convertEsIndexNotFoundError(indices, indexNotFoundError); + const converted = convertEsError(indices, indexNotFoundError); if (!isNoMatchingIndicesError(converted)) { - throw new Error('expected convertEsIndexNotFoundError(indexNotFoundError) to return NoMatchingIndices error'); + throw new Error('expected convertEsError(indexNotFoundError) to return NoMatchingIndices error'); } }); - it('returns other errors', async () => { - const originals = [docNotFoundError, '', 1, /foo/, new Date(), new Error(), function () {}]; - - originals.forEach(orig => { - const converted = convertEsIndexNotFoundError(indices, orig); - if (converted !== orig) { - throw new Error(`expected convertEsIndexNotFoundError(${orig}) to return original error`); - } + it('wraps other errors in Boom', async () => { + const error = new esErrors.AuthenticationException({ + root_cause: [ + { + type: 'security_exception', + reason: 'action [indices:data/read/field_caps] is unauthorized for user [standard]' + } + ], + type: 'security_exception', + reason: 'action [indices:data/read/field_caps] is unauthorized for user [standard]' + }, { + statusCode: 403 }); + + expect(error).to.not.have.property('isBoom'); + const converted = convertEsError(indices, error); + expect(converted).to.have.property('isBoom'); + expect(converted.output.statusCode).to.be(403); }); }); });