mirror of
https://github.com/elastic/kibana.git
synced 2025-04-24 09:48:58 -04:00
# Backport This will backport the following commits from `main` to `7.17`: - [[json layout] use json representation of `meta` when available (#171310)](https://github.com/elastic/kibana/pull/171310) <!--- Backport version: 8.9.8 --> ### Questions ? Please refer to the [Backport tool documentation](https://github.com/sqren/backport) <!--BACKPORT [{"author":{"name":"Pierre Gayvallet","email":"pierre.gayvallet@elastic.co"},"sourceCommit":{"committedDate":"2023-11-15T18:27:52Z","message":"[json layout] use json representation of `meta` when available (#171310)\n\n## Summary\r\n\r\nUse the json representation (`toJSON`) of the log's `meta` when merging\r\nthe message and the meta, if possible.","sha":"3d6ac9d46a64d7f14acd75523706aa2bd33c2aef","branchLabelMapping":{"^v8.12.0$":"main","^v(\\d+).(\\d+).\\d+$":"$1.$2"}},"sourcePullRequest":{"labels":["release_note:skip","Feature:Logging","backport:prev-minor","backport:prev-MAJOR","v8.12.0"],"number":171310,"url":"https://github.com/elastic/kibana/pull/171310","mergeCommit":{"message":"[json layout] use json representation of `meta` when available (#171310)\n\n## Summary\r\n\r\nUse the json representation (`toJSON`) of the log's `meta` when merging\r\nthe message and the meta, if possible.","sha":"3d6ac9d46a64d7f14acd75523706aa2bd33c2aef"}},"sourceBranch":"main","suggestedTargetBranches":[],"targetPullRequestStates":[{"branch":"main","label":"v8.12.0","labelRegex":"^v8.12.0$","isSourceBranch":true,"state":"MERGED","url":"https://github.com/elastic/kibana/pull/171310","number":171310,"mergeCommit":{"message":"[json layout] use json representation of `meta` when available (#171310)\n\n## Summary\r\n\r\nUse the json representation (`toJSON`) of the log's `meta` when merging\r\nthe message and the meta, if possible.","sha":"3d6ac9d46a64d7f14acd75523706aa2bd33c2aef"}},{"url":"https://github.com/elastic/kibana/pull/171343","number":171343,"branch":"8.11","state":"OPEN"}]}] BACKPORT-->
This commit is contained in:
parent
a28849a83e
commit
3f5c10e9da
3 changed files with 185 additions and 1 deletions
|
@ -0,0 +1,94 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0 and the Server Side Public License, v 1; you may not use this file except
|
||||
* in compliance with, at your election, the Elastic License 2.0 or the Server
|
||||
* Side Public License, v 1.
|
||||
*/
|
||||
|
||||
import {
|
||||
createTestServers,
|
||||
type TestElasticsearchUtils,
|
||||
type TestKibanaUtils,
|
||||
} from '../../../test_helpers/kbn_server';
|
||||
|
||||
describe('Error logging', () => {
|
||||
describe('ES client errors', () => {
|
||||
let mockConsoleLog: jest.SpyInstance;
|
||||
let esServer: TestElasticsearchUtils;
|
||||
let kibanaServer: TestKibanaUtils;
|
||||
|
||||
beforeAll(async () => {
|
||||
mockConsoleLog = jest.spyOn(global.console, 'log');
|
||||
|
||||
const { startES, startKibana } = createTestServers({
|
||||
adjustTimeout: jest.setTimeout,
|
||||
settings: {
|
||||
kbn: {
|
||||
logging: {
|
||||
appenders: {
|
||||
'console-json': {
|
||||
type: 'console',
|
||||
layout: {
|
||||
type: 'json',
|
||||
},
|
||||
},
|
||||
},
|
||||
loggers: [{ name: 'console-json', appenders: ['console-json'], level: 'debug' }],
|
||||
},
|
||||
},
|
||||
},
|
||||
});
|
||||
|
||||
esServer = await startES();
|
||||
kibanaServer = await startKibana();
|
||||
});
|
||||
|
||||
beforeEach(() => {
|
||||
mockConsoleLog.mockClear();
|
||||
});
|
||||
|
||||
afterAll(async () => {
|
||||
mockConsoleLog.mockRestore();
|
||||
await kibanaServer.stop();
|
||||
await esServer.stop();
|
||||
});
|
||||
|
||||
it('logs errors following the expected pattern for the json layout', async () => {
|
||||
const esClient = kibanaServer.coreStart.elasticsearch.client.asInternalUser;
|
||||
const logger = kibanaServer.root.logger.get('console-json');
|
||||
|
||||
try {
|
||||
await esClient.search({
|
||||
index: '.kibana',
|
||||
// @ts-expect-error yes this is invalid
|
||||
query: { someInvalidQuery: { foo: 'bar' } },
|
||||
});
|
||||
expect('should have thrown').toEqual('but it did not');
|
||||
} catch (e) {
|
||||
logger.info('logging elasticsearch error', e);
|
||||
|
||||
const calls = mockConsoleLog.mock.calls;
|
||||
const ourCall = calls
|
||||
.map((call) => call[0])
|
||||
.find((call) => call.includes('logging elasticsearch error'));
|
||||
|
||||
expect(JSON.parse(ourCall)).toEqual({
|
||||
'@timestamp': expect.any(String),
|
||||
ecs: {
|
||||
version: expect.any(String),
|
||||
},
|
||||
log: {
|
||||
level: 'INFO',
|
||||
logger: 'console-json',
|
||||
},
|
||||
message: 'logging elasticsearch error',
|
||||
name: 'ResponseError',
|
||||
process: {
|
||||
pid: expect.any(Number),
|
||||
},
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
|
@ -308,3 +308,88 @@ test('format() meta can not override timestamp', () => {
|
|||
},
|
||||
});
|
||||
});
|
||||
|
||||
test('format() meta.toJSON() is used if own property', () => {
|
||||
const layout = new JsonLayout();
|
||||
expect(
|
||||
JSON.parse(
|
||||
layout.format({
|
||||
message: 'foo',
|
||||
timestamp,
|
||||
level: LogLevel.Debug,
|
||||
context: 'bar',
|
||||
pid: 3,
|
||||
meta: {
|
||||
server: {
|
||||
address: 'localhost',
|
||||
},
|
||||
service: {
|
||||
version: '1',
|
||||
},
|
||||
toJSON() {
|
||||
return {
|
||||
server: {
|
||||
address: 'localhost',
|
||||
},
|
||||
};
|
||||
},
|
||||
},
|
||||
})
|
||||
)
|
||||
).toStrictEqual({
|
||||
ecs: { version: expect.any(String) },
|
||||
'@timestamp': '2012-02-01T09:30:22.011-05:00',
|
||||
message: 'foo',
|
||||
log: {
|
||||
level: 'DEBUG',
|
||||
logger: 'bar',
|
||||
},
|
||||
process: {
|
||||
pid: 3,
|
||||
},
|
||||
server: {
|
||||
address: 'localhost',
|
||||
},
|
||||
});
|
||||
});
|
||||
|
||||
test('format() meta.toJSON() is used if present on prototype', () => {
|
||||
class SomeClass {
|
||||
foo: string = 'bar';
|
||||
hello: string = 'dolly';
|
||||
|
||||
toJSON() {
|
||||
return {
|
||||
foo: this.foo,
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
const someInstance = new SomeClass();
|
||||
|
||||
const layout = new JsonLayout();
|
||||
expect(
|
||||
JSON.parse(
|
||||
layout.format({
|
||||
message: 'foo',
|
||||
timestamp,
|
||||
level: LogLevel.Debug,
|
||||
context: 'bar',
|
||||
pid: 3,
|
||||
meta: someInstance,
|
||||
})
|
||||
)
|
||||
).toStrictEqual({
|
||||
ecs: { version: expect.any(String) },
|
||||
'@timestamp': '2012-02-01T09:30:22.011-05:00',
|
||||
message: 'foo',
|
||||
log: {
|
||||
level: 'DEBUG',
|
||||
logger: 'bar',
|
||||
},
|
||||
process: {
|
||||
pid: 3,
|
||||
},
|
||||
foo: 'bar',
|
||||
});
|
||||
});
|
||||
|
|
|
@ -55,7 +55,12 @@ export class JsonLayout implements Layout {
|
|||
pid: record.pid,
|
||||
},
|
||||
};
|
||||
const output = record.meta ? merge({ ...record.meta }, log) : log;
|
||||
|
||||
let output = log;
|
||||
if (record.meta) {
|
||||
const serializedMeta = record.meta.toJSON ? record.meta.toJSON() : { ...record.meta };
|
||||
output = merge(serializedMeta, log);
|
||||
}
|
||||
|
||||
return JSON.stringify(output);
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue