From 77f0fda5272bc3e690e66a7819f0faeada4b75ea Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alejandro=20Fern=C3=A1ndez=20G=C3=B3mez?= Date: Mon, 26 Oct 2020 21:40:45 +0100 Subject: [PATCH] Tweak log item API The values will be returned as arrays of strings to match the response of the log entries API. The UI is now responsible to decide how render the fields. --- .../infra/common/http_api/log_entries/item.ts | 2 +- .../log_entry_flyout/log_entry_flyout.tsx | 6 ++- ...document_source_to_log_item_fields.test.ts | 46 ++++++++-------- ...vert_document_source_to_log_item_fields.ts | 33 ++++-------- .../log_entries_domain/log_entries_domain.ts | 4 +- .../apis/metrics_ui/log_item.ts | 52 +++++++++---------- 6 files changed, 64 insertions(+), 79 deletions(-) diff --git a/x-pack/plugins/infra/common/http_api/log_entries/item.ts b/x-pack/plugins/infra/common/http_api/log_entries/item.ts index 02335d68402c0..5f9457b8228ac 100644 --- a/x-pack/plugins/infra/common/http_api/log_entries/item.ts +++ b/x-pack/plugins/infra/common/http_api/log_entries/item.ts @@ -16,7 +16,7 @@ export const logEntriesItemRequestRT = rt.type({ export type LogEntriesItemRequest = rt.TypeOf; -const logEntriesItemFieldRT = rt.type({ field: rt.string, value: rt.string }); +const logEntriesItemFieldRT = rt.type({ field: rt.string, value: rt.array(rt.string) }); const logEntriesItemRT = rt.type({ id: rt.string, index: rt.string, diff --git a/x-pack/plugins/infra/public/components/logging/log_entry_flyout/log_entry_flyout.tsx b/x-pack/plugins/infra/public/components/logging/log_entry_flyout/log_entry_flyout.tsx index 76ffada510e51..b07d8c9dce23c 100644 --- a/x-pack/plugins/infra/public/components/logging/log_entry_flyout/log_entry_flyout.tsx +++ b/x-pack/plugins/infra/public/components/logging/log_entry_flyout/log_entry_flyout.tsx @@ -94,7 +94,7 @@ export const LogEntryFlyout = ({ onClick={createFilterHandler(item)} /> - {item.value} + {formatValue(item.value)} ), }, @@ -147,3 +147,7 @@ export const InfraFlyoutLoadingPanel = euiStyled.div` bottom: 0; left: 0; `; + +function formatValue(value: string[]) { + return value.length > 1 ? value.join(', ') : value[0]; +} diff --git a/x-pack/plugins/infra/server/lib/domains/log_entries_domain/convert_document_source_to_log_item_fields.test.ts b/x-pack/plugins/infra/server/lib/domains/log_entries_domain/convert_document_source_to_log_item_fields.test.ts index 98d1e2cd89b01..7b79a1bf0386a 100644 --- a/x-pack/plugins/infra/server/lib/domains/log_entries_domain/convert_document_source_to_log_item_fields.test.ts +++ b/x-pack/plugins/infra/server/lib/domains/log_entries_domain/convert_document_source_to_log_item_fields.test.ts @@ -4,66 +4,62 @@ * you may not use this file except in compliance with the Elastic License. */ -import { convertDocumentSourceToLogItemFields } from './convert_document_source_to_log_item_fields'; +import { convertESFieldsToLogItemFields } from './convert_document_source_to_log_item_fields'; -describe('convertDocumentSourceToLogItemFields', () => { - test('should convert document', () => { - const doc = { - agent: { - hostname: 'demo-stack-client-01', - id: '7adef8b6-2ab7-45cd-a0d5-b3baad735f1b', - type: 'filebeat', - ephemeral_id: 'a0c8164b-3564-4e32-b0bf-f4db5a7ae566', - version: '7.0.0', - }, +describe('convertESFieldsToLogItemFields', () => { + test('Converts the fields collection to LogItemFields', () => { + const esFields = { + 'agent.hostname': ['demo-stack-client-01'], + 'agent.id': ['7adef8b6-2ab7-45cd-a0d5-b3baad735f1b'], + 'agent.type': ['filebeat'], + 'agent.ephemeral_id': ['a0c8164b-3564-4e32-b0bf-f4db5a7ae566'], + 'agent.version': ['7.0.0'], tags: ['prod', 'web'], metadata: [ { key: 'env', value: 'prod' }, { key: 'stack', value: 'web' }, ], - host: { - hostname: 'packer-virtualbox-iso-1546820004', - name: 'demo-stack-client-01', - }, + 'host.hostname': ['packer-virtualbox-iso-1546820004'], + 'host.name': ['demo-stack-client-01'], }; - const fields = convertDocumentSourceToLogItemFields(doc); + const fields = convertESFieldsToLogItemFields(esFields); expect(fields).toEqual([ { field: 'agent.hostname', - value: 'demo-stack-client-01', + value: ['demo-stack-client-01'], }, { field: 'agent.id', - value: '7adef8b6-2ab7-45cd-a0d5-b3baad735f1b', + value: ['7adef8b6-2ab7-45cd-a0d5-b3baad735f1b'], }, { field: 'agent.type', - value: 'filebeat', + value: ['filebeat'], }, { field: 'agent.ephemeral_id', - value: 'a0c8164b-3564-4e32-b0bf-f4db5a7ae566', + value: ['a0c8164b-3564-4e32-b0bf-f4db5a7ae566'], }, { field: 'agent.version', - value: '7.0.0', + value: ['7.0.0'], }, { field: 'tags', - value: '["prod","web"]', + value: ['prod', 'web'], }, { field: 'metadata', - value: '[{"key":"env","value":"prod"},{"key":"stack","value":"web"}]', + value: ['{"key":"env","value":"prod"}', '{"key":"stack","value":"web"}'], }, { field: 'host.hostname', - value: 'packer-virtualbox-iso-1546820004', + value: ['packer-virtualbox-iso-1546820004'], }, { field: 'host.name', - value: 'demo-stack-client-01', + value: ['demo-stack-client-01'], }, ]); }); diff --git a/x-pack/plugins/infra/server/lib/domains/log_entries_domain/convert_document_source_to_log_item_fields.ts b/x-pack/plugins/infra/server/lib/domains/log_entries_domain/convert_document_source_to_log_item_fields.ts index af5776c8582ed..a1d855bfdaa48 100644 --- a/x-pack/plugins/infra/server/lib/domains/log_entries_domain/convert_document_source_to_log_item_fields.ts +++ b/x-pack/plugins/infra/server/lib/domains/log_entries_domain/convert_document_source_to_log_item_fields.ts @@ -6,35 +6,20 @@ import stringify from 'json-stable-stringify'; import { LogEntriesItemField } from '../../../../common/http_api'; -import { JsonArray, JsonObject, jsonObjectRT, JsonValue } from '../../../../common/typed_json'; +import { JsonArray } from '../../../../common/typed_json'; -const serializeValue = (value: JsonValue): string => { - if (typeof value === 'object' && value != null) { - return stringify(value); - } else { - return `${value}`; - } +const serializeValue = (value: JsonArray): string[] => { + return value.map((v) => { + if (typeof v === 'object' && v != null) { + return stringify(v); + } else { + return `${v}`; + } + }); }; -// TODO: move rendering to browser export const convertESFieldsToLogItemFields = (fields: { [field: string]: JsonArray; }): LogEntriesItemField[] => { return Object.keys(fields).map((field) => ({ field, value: serializeValue(fields[field]) })); }; - -export const convertDocumentSourceToLogItemFields = ( - source: JsonObject, - path: string[] = [], - fields: LogEntriesItemField[] = [] -): LogEntriesItemField[] => { - return Object.keys(source).reduce((acc, key) => { - const value = source[key]; - const nextPath = [...path, key]; - if (jsonObjectRT.is(value)) { - return convertDocumentSourceToLogItemFields(value, nextPath, acc); - } - const field = { field: nextPath.join('.'), value: serializeValue(value) }; - return [...acc, field]; - }, fields); -}; diff --git a/x-pack/plugins/infra/server/lib/domains/log_entries_domain/log_entries_domain.ts b/x-pack/plugins/infra/server/lib/domains/log_entries_domain/log_entries_domain.ts index 931a073dfaeb7..cc9d4c749c77d 100644 --- a/x-pack/plugins/infra/server/lib/domains/log_entries_domain/log_entries_domain.ts +++ b/x-pack/plugins/infra/server/lib/domains/log_entries_domain/log_entries_domain.ts @@ -252,8 +252,8 @@ export class InfraLogEntriesDomain { ): Promise { const document = await this.adapter.getLogItem(requestContext, id, sourceConfiguration); const defaultFields = [ - { field: '_index', value: document._index }, - { field: '_id', value: document._id }, + { field: '_index', value: [document._index] }, + { field: '_id', value: [document._id] }, ]; return { diff --git a/x-pack/test/api_integration/apis/metrics_ui/log_item.ts b/x-pack/test/api_integration/apis/metrics_ui/log_item.ts index 6e0148f13277c..3bb7a9a76690d 100644 --- a/x-pack/test/api_integration/apis/metrics_ui/log_item.ts +++ b/x-pack/test/api_integration/apis/metrics_ui/log_item.ts @@ -44,107 +44,107 @@ export default function ({ getService }: FtrProviderContext) { expect(logItem.fields).to.eql([ { field: '@timestamp', - value: '2018-10-17T19:42:22.000Z', + value: ['2018-10-17T19:42:22.000Z'], }, { field: '_id', - value: 'yT2Mg2YBh-opCxJv8Vqj', + value: ['yT2Mg2YBh-opCxJv8Vqj'], }, { field: '_index', - value: 'filebeat-7.0.0-alpha1-2018.10.17', + value: ['filebeat-7.0.0-alpha1-2018.10.17'], }, { field: 'apache2.access.body_sent.bytes', - value: '1336', + value: ['1336'], }, { field: 'apache2.access.http_version', - value: '1.1', + value: ['1.1'], }, { field: 'apache2.access.method', - value: 'GET', + value: ['GET'], }, { field: 'apache2.access.referrer', - value: '-', + value: ['-'], }, { field: 'apache2.access.remote_ip', - value: '10.128.0.11', + value: ['10.128.0.11'], }, { field: 'apache2.access.response_code', - value: '200', + value: ['200'], }, { field: 'apache2.access.url', - value: '/a-fresh-start-will-put-you-on-your-way', + value: ['/a-fresh-start-will-put-you-on-your-way'], }, { field: 'apache2.access.user_agent.device', - value: 'Other', + value: ['Other'], }, { field: 'apache2.access.user_agent.name', - value: 'Other', + value: ['Other'], }, { field: 'apache2.access.user_agent.os', - value: 'Other', + value: ['Other'], }, { field: 'apache2.access.user_agent.os_name', - value: 'Other', + value: ['Other'], }, { field: 'apache2.access.user_name', - value: '-', + value: ['-'], }, { field: 'beat.hostname', - value: 'demo-stack-apache-01', + value: ['demo-stack-apache-01'], }, { field: 'beat.name', - value: 'demo-stack-apache-01', + value: ['demo-stack-apache-01'], }, { field: 'beat.version', - value: '7.0.0-alpha1', + value: ['7.0.0-alpha1'], }, { field: 'fileset.module', - value: 'apache2', + value: ['apache2'], }, { field: 'fileset.name', - value: 'access', + value: ['access'], }, { field: 'host.name', - value: 'demo-stack-apache-01', + value: ['demo-stack-apache-01'], }, { field: 'input.type', - value: 'log', + value: ['log'], }, { field: 'offset', - value: '5497614', + value: ['5497614'], }, { field: 'prospector.type', - value: 'log', + value: ['log'], }, { field: 'read_timestamp', - value: '2018-10-17T19:42:23.160Z', + value: ['2018-10-17T19:42:23.160Z'], }, { field: 'source', - value: '/var/log/apache2/access.log', + value: ['/var/log/apache2/access.log'], }, ]); });