mirror of
https://github.com/grafana/grafana.git
synced 2024-11-25 18:30:41 -06:00
Explore: Add switch to restructure logs for better readability (#36324)
* Add prettifyLogMessage to select components in test file * Change entry depending on the value of prettifyLogMessage * Add prettifyLogMessage to state * Fix merge conflict * Fixe bug where the log message wasn't parsed as JSON * Implement function to restructure all logs * Change elstic image version back to 7.7.1 * Add showCommonLabels that was missing * Remove comment * Put import of getParser together with the other imports * Logs: fix bug where message isn't restructured if it contains ANSI code * Logs: change label for switch to Restructure * Remove unnecessary file * Logs: added divider before switch component * Add dividers between the different log options * Remove unintentional changes * Explore: remove dividers in log settings * Explore: refactor for LogRowMessage for better readability * remove unnecessary change * Logs: fix bug where logs aren't restructured if they have highlights * Logs: minor refactoring * Logs: use memoizeOne to prevent parsing on every re-render * Logs: calculate needsHilight inside renderLogMessage instead of outside * Logs: fix bug where logs aren't prettified when wrap logs is disabled * Explore: change name to prettify * Remove console.log Co-authored-by: Ivana Huckova <30407135+ivanahuckova@users.noreply.github.com> * Dashboards: add switch to prettify log messages to the Logs fields * Logs: make prettify only work for JSON logs * Logs: fix bug with tests for logs * Update public/app/plugins/panel/logs/module.tsx Co-authored-by: Ivana Huckova <30407135+ivanahuckova@users.noreply.github.com> Co-authored-by: Ivana Huckova <30407135+ivanahuckova@users.noreply.github.com>
This commit is contained in:
parent
96efbbaed1
commit
f4f2c197ae
@ -40,6 +40,7 @@ interface Props extends Themeable {
|
|||||||
showLabels: boolean;
|
showLabels: boolean;
|
||||||
showTime: boolean;
|
showTime: boolean;
|
||||||
wrapLogMessage: boolean;
|
wrapLogMessage: boolean;
|
||||||
|
prettifyLogMessage: boolean;
|
||||||
timeZone: TimeZone;
|
timeZone: TimeZone;
|
||||||
enableLogDetails: boolean;
|
enableLogDetails: boolean;
|
||||||
logsSortOrder?: LogsSortOrder | null;
|
logsSortOrder?: LogsSortOrder | null;
|
||||||
@ -139,6 +140,7 @@ class UnThemedLogRow extends PureComponent<Props, State> {
|
|||||||
showTime,
|
showTime,
|
||||||
showDetectedFields,
|
showDetectedFields,
|
||||||
wrapLogMessage,
|
wrapLogMessage,
|
||||||
|
prettifyLogMessage,
|
||||||
theme,
|
theme,
|
||||||
getFieldLinks,
|
getFieldLinks,
|
||||||
forceEscape,
|
forceEscape,
|
||||||
@ -201,6 +203,7 @@ class UnThemedLogRow extends PureComponent<Props, State> {
|
|||||||
contextIsOpen={showContext}
|
contextIsOpen={showContext}
|
||||||
showContextToggle={showContextToggle}
|
showContextToggle={showContextToggle}
|
||||||
wrapLogMessage={wrapLogMessage}
|
wrapLogMessage={wrapLogMessage}
|
||||||
|
prettifyLogMessage={prettifyLogMessage}
|
||||||
onToggleContext={this.toggleContext}
|
onToggleContext={this.toggleContext}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
|
@ -3,6 +3,7 @@ import { isEqual } from 'lodash';
|
|||||||
import tinycolor from 'tinycolor2';
|
import tinycolor from 'tinycolor2';
|
||||||
import { css, cx } from '@emotion/css';
|
import { css, cx } from '@emotion/css';
|
||||||
import { LogRowModel, findHighlightChunksInText, GrafanaTheme } from '@grafana/data';
|
import { LogRowModel, findHighlightChunksInText, GrafanaTheme } from '@grafana/data';
|
||||||
|
import memoizeOne from 'memoize-one';
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
import Highlighter from 'react-highlight-words';
|
import Highlighter from 'react-highlight-words';
|
||||||
@ -23,6 +24,7 @@ interface Props extends Themeable {
|
|||||||
hasMoreContextRows?: HasMoreContextRows;
|
hasMoreContextRows?: HasMoreContextRows;
|
||||||
contextIsOpen: boolean;
|
contextIsOpen: boolean;
|
||||||
wrapLogMessage: boolean;
|
wrapLogMessage: boolean;
|
||||||
|
prettifyLogMessage: boolean;
|
||||||
errors?: LogRowContextQueryErrors;
|
errors?: LogRowContextQueryErrors;
|
||||||
context?: LogRowContextRows;
|
context?: LogRowContextRows;
|
||||||
showContextToggle?: (row?: LogRowModel) => boolean;
|
showContextToggle?: (row?: LogRowModel) => boolean;
|
||||||
@ -47,11 +49,46 @@ const getStyles = stylesFactory((theme: GrafanaTheme) => {
|
|||||||
`,
|
`,
|
||||||
horizontalScroll: css`
|
horizontalScroll: css`
|
||||||
label: verticalScroll;
|
label: verticalScroll;
|
||||||
white-space: nowrap;
|
white-space: pre;
|
||||||
`,
|
`,
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
|
function renderLogMessage(
|
||||||
|
hasAnsi: boolean,
|
||||||
|
entry: string,
|
||||||
|
highlights: string[] | undefined,
|
||||||
|
highlightClassName: string
|
||||||
|
) {
|
||||||
|
const needsHighlighter =
|
||||||
|
highlights && highlights.length > 0 && highlights[0] && highlights[0].length > 0 && entry.length < MAX_CHARACTERS;
|
||||||
|
if (needsHighlighter) {
|
||||||
|
return (
|
||||||
|
<Highlighter
|
||||||
|
textToHighlight={entry}
|
||||||
|
searchWords={highlights ?? []}
|
||||||
|
findChunks={findHighlightChunksInText}
|
||||||
|
highlightClassName={highlightClassName}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
} else if (hasAnsi) {
|
||||||
|
return <LogMessageAnsi value={entry} />;
|
||||||
|
} else {
|
||||||
|
return entry;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const restructureLog = memoizeOne((line: string, prettifyLogMessage: boolean): string => {
|
||||||
|
if (prettifyLogMessage) {
|
||||||
|
try {
|
||||||
|
return JSON.stringify(JSON.parse(line), undefined, 2);
|
||||||
|
} catch (error) {
|
||||||
|
return line;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return line;
|
||||||
|
});
|
||||||
|
|
||||||
class UnThemedLogRowMessage extends PureComponent<Props> {
|
class UnThemedLogRowMessage extends PureComponent<Props> {
|
||||||
onContextToggle = (e: React.SyntheticEvent<HTMLElement>) => {
|
onContextToggle = (e: React.SyntheticEvent<HTMLElement>) => {
|
||||||
e.stopPropagation();
|
e.stopPropagation();
|
||||||
@ -70,16 +107,16 @@ class UnThemedLogRowMessage extends PureComponent<Props> {
|
|||||||
contextIsOpen,
|
contextIsOpen,
|
||||||
showContextToggle,
|
showContextToggle,
|
||||||
wrapLogMessage,
|
wrapLogMessage,
|
||||||
|
prettifyLogMessage,
|
||||||
onToggleContext,
|
onToggleContext,
|
||||||
} = this.props;
|
} = this.props;
|
||||||
|
|
||||||
const style = getLogRowStyles(theme, row.logLevel);
|
const style = getLogRowStyles(theme, row.logLevel);
|
||||||
const { entry, hasAnsi, raw } = row;
|
const { hasAnsi, raw } = row;
|
||||||
|
const restructuredEntry = restructureLog(raw, prettifyLogMessage);
|
||||||
|
|
||||||
const previewHighlights = highlighterExpressions?.length && !isEqual(highlighterExpressions, row.searchWords);
|
const previewHighlights = highlighterExpressions?.length && !isEqual(highlighterExpressions, row.searchWords);
|
||||||
const highlights = previewHighlights ? highlighterExpressions : row.searchWords;
|
const highlights = previewHighlights ? highlighterExpressions : row.searchWords;
|
||||||
const needsHighlighter =
|
|
||||||
highlights && highlights.length > 0 && highlights[0] && highlights[0].length > 0 && entry.length < MAX_CHARACTERS;
|
|
||||||
const highlightClassName = previewHighlights
|
const highlightClassName = previewHighlights
|
||||||
? cx([style.logsRowMatchHighLight, style.logsRowMatchHighLightPreview])
|
? cx([style.logsRowMatchHighLight, style.logsRowMatchHighLightPreview])
|
||||||
: cx([style.logsRowMatchHighLight]);
|
: cx([style.logsRowMatchHighLight]);
|
||||||
@ -103,18 +140,7 @@ class UnThemedLogRowMessage extends PureComponent<Props> {
|
|||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
<span className={cx(styles.positionRelative, { [styles.rowWithContext]: contextIsOpen })}>
|
<span className={cx(styles.positionRelative, { [styles.rowWithContext]: contextIsOpen })}>
|
||||||
{needsHighlighter ? (
|
{renderLogMessage(hasAnsi, restructuredEntry, highlights, highlightClassName)}
|
||||||
<Highlighter
|
|
||||||
textToHighlight={entry}
|
|
||||||
searchWords={highlights ?? []}
|
|
||||||
findChunks={findHighlightChunksInText}
|
|
||||||
highlightClassName={highlightClassName}
|
|
||||||
/>
|
|
||||||
) : hasAnsi ? (
|
|
||||||
<LogMessageAnsi value={raw} />
|
|
||||||
) : (
|
|
||||||
entry
|
|
||||||
)}
|
|
||||||
</span>
|
</span>
|
||||||
{showContextToggle?.(row) && (
|
{showContextToggle?.(row) && (
|
||||||
<span onClick={this.onContextToggle} className={cx('log-row-context', style.context)}>
|
<span onClick={this.onContextToggle} className={cx('log-row-context', style.context)}>
|
||||||
|
@ -16,6 +16,7 @@ describe('LogRows', () => {
|
|||||||
showLabels={false}
|
showLabels={false}
|
||||||
showTime={false}
|
showTime={false}
|
||||||
wrapLogMessage={true}
|
wrapLogMessage={true}
|
||||||
|
prettifyLogMessage={true}
|
||||||
timeZone={'utc'}
|
timeZone={'utc'}
|
||||||
enableLogDetails={true}
|
enableLogDetails={true}
|
||||||
/>
|
/>
|
||||||
@ -38,6 +39,7 @@ describe('LogRows', () => {
|
|||||||
showLabels={false}
|
showLabels={false}
|
||||||
showTime={false}
|
showTime={false}
|
||||||
wrapLogMessage={true}
|
wrapLogMessage={true}
|
||||||
|
prettifyLogMessage={true}
|
||||||
timeZone={'utc'}
|
timeZone={'utc'}
|
||||||
previewLimit={1}
|
previewLimit={1}
|
||||||
enableLogDetails={true}
|
enableLogDetails={true}
|
||||||
@ -69,6 +71,7 @@ describe('LogRows', () => {
|
|||||||
showLabels={false}
|
showLabels={false}
|
||||||
showTime={false}
|
showTime={false}
|
||||||
wrapLogMessage={true}
|
wrapLogMessage={true}
|
||||||
|
prettifyLogMessage={true}
|
||||||
timeZone={'utc'}
|
timeZone={'utc'}
|
||||||
enableLogDetails={true}
|
enableLogDetails={true}
|
||||||
/>
|
/>
|
||||||
@ -90,6 +93,7 @@ describe('LogRows', () => {
|
|||||||
showLabels={false}
|
showLabels={false}
|
||||||
showTime={false}
|
showTime={false}
|
||||||
wrapLogMessage={true}
|
wrapLogMessage={true}
|
||||||
|
prettifyLogMessage={true}
|
||||||
timeZone={'utc'}
|
timeZone={'utc'}
|
||||||
enableLogDetails={true}
|
enableLogDetails={true}
|
||||||
/>
|
/>
|
||||||
@ -112,6 +116,7 @@ describe('LogRows', () => {
|
|||||||
showLabels={false}
|
showLabels={false}
|
||||||
showTime={false}
|
showTime={false}
|
||||||
wrapLogMessage={true}
|
wrapLogMessage={true}
|
||||||
|
prettifyLogMessage={true}
|
||||||
timeZone={'utc'}
|
timeZone={'utc'}
|
||||||
logsSortOrder={LogsSortOrder.Ascending}
|
logsSortOrder={LogsSortOrder.Ascending}
|
||||||
enableLogDetails={true}
|
enableLogDetails={true}
|
||||||
@ -136,6 +141,7 @@ describe('LogRows', () => {
|
|||||||
showLabels={false}
|
showLabels={false}
|
||||||
showTime={false}
|
showTime={false}
|
||||||
wrapLogMessage={true}
|
wrapLogMessage={true}
|
||||||
|
prettifyLogMessage={true}
|
||||||
timeZone={'utc'}
|
timeZone={'utc'}
|
||||||
logsSortOrder={LogsSortOrder.Descending}
|
logsSortOrder={LogsSortOrder.Descending}
|
||||||
enableLogDetails={true}
|
enableLogDetails={true}
|
||||||
|
@ -20,6 +20,7 @@ export interface Props extends Themeable {
|
|||||||
showLabels: boolean;
|
showLabels: boolean;
|
||||||
showTime: boolean;
|
showTime: boolean;
|
||||||
wrapLogMessage: boolean;
|
wrapLogMessage: boolean;
|
||||||
|
prettifyLogMessage: boolean;
|
||||||
timeZone: TimeZone;
|
timeZone: TimeZone;
|
||||||
enableLogDetails: boolean;
|
enableLogDetails: boolean;
|
||||||
logsSortOrder?: LogsSortOrder | null;
|
logsSortOrder?: LogsSortOrder | null;
|
||||||
@ -84,6 +85,7 @@ class UnThemedLogRows extends PureComponent<Props, State> {
|
|||||||
showLabels,
|
showLabels,
|
||||||
showTime,
|
showTime,
|
||||||
wrapLogMessage,
|
wrapLogMessage,
|
||||||
|
prettifyLogMessage,
|
||||||
logRows,
|
logRows,
|
||||||
deduplicatedRows,
|
deduplicatedRows,
|
||||||
highlighterExpressions,
|
highlighterExpressions,
|
||||||
@ -135,6 +137,7 @@ class UnThemedLogRows extends PureComponent<Props, State> {
|
|||||||
showTime={showTime}
|
showTime={showTime}
|
||||||
showDetectedFields={showDetectedFields}
|
showDetectedFields={showDetectedFields}
|
||||||
wrapLogMessage={wrapLogMessage}
|
wrapLogMessage={wrapLogMessage}
|
||||||
|
prettifyLogMessage={prettifyLogMessage}
|
||||||
timeZone={timeZone}
|
timeZone={timeZone}
|
||||||
enableLogDetails={enableLogDetails}
|
enableLogDetails={enableLogDetails}
|
||||||
onClickFilterLabel={onClickFilterLabel}
|
onClickFilterLabel={onClickFilterLabel}
|
||||||
@ -160,6 +163,7 @@ class UnThemedLogRows extends PureComponent<Props, State> {
|
|||||||
showTime={showTime}
|
showTime={showTime}
|
||||||
showDetectedFields={showDetectedFields}
|
showDetectedFields={showDetectedFields}
|
||||||
wrapLogMessage={wrapLogMessage}
|
wrapLogMessage={wrapLogMessage}
|
||||||
|
prettifyLogMessage={prettifyLogMessage}
|
||||||
timeZone={timeZone}
|
timeZone={timeZone}
|
||||||
enableLogDetails={enableLogDetails}
|
enableLogDetails={enableLogDetails}
|
||||||
onClickFilterLabel={onClickFilterLabel}
|
onClickFilterLabel={onClickFilterLabel}
|
||||||
|
@ -42,6 +42,7 @@ const SETTINGS_KEYS = {
|
|||||||
showLabels: 'grafana.explore.logs.showLabels',
|
showLabels: 'grafana.explore.logs.showLabels',
|
||||||
showTime: 'grafana.explore.logs.showTime',
|
showTime: 'grafana.explore.logs.showTime',
|
||||||
wrapLogMessage: 'grafana.explore.logs.wrapLogMessage',
|
wrapLogMessage: 'grafana.explore.logs.wrapLogMessage',
|
||||||
|
prettifyLogMessage: 'grafana.explore.logs.prettifyLogMessage',
|
||||||
};
|
};
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
@ -74,6 +75,7 @@ interface State {
|
|||||||
showLabels: boolean;
|
showLabels: boolean;
|
||||||
showTime: boolean;
|
showTime: boolean;
|
||||||
wrapLogMessage: boolean;
|
wrapLogMessage: boolean;
|
||||||
|
prettifyLogMessage: boolean;
|
||||||
dedupStrategy: LogsDedupStrategy;
|
dedupStrategy: LogsDedupStrategy;
|
||||||
hiddenLogLevels: LogLevel[];
|
hiddenLogLevels: LogLevel[];
|
||||||
logsSortOrder: LogsSortOrder | null;
|
logsSortOrder: LogsSortOrder | null;
|
||||||
@ -91,6 +93,7 @@ export class UnthemedLogs extends PureComponent<Props, State> {
|
|||||||
showLabels: store.getBool(SETTINGS_KEYS.showLabels, false),
|
showLabels: store.getBool(SETTINGS_KEYS.showLabels, false),
|
||||||
showTime: store.getBool(SETTINGS_KEYS.showTime, true),
|
showTime: store.getBool(SETTINGS_KEYS.showTime, true),
|
||||||
wrapLogMessage: store.getBool(SETTINGS_KEYS.wrapLogMessage, true),
|
wrapLogMessage: store.getBool(SETTINGS_KEYS.wrapLogMessage, true),
|
||||||
|
prettifyLogMessage: store.getBool(SETTINGS_KEYS.prettifyLogMessage, false),
|
||||||
dedupStrategy: LogsDedupStrategy.none,
|
dedupStrategy: LogsDedupStrategy.none,
|
||||||
hiddenLogLevels: [],
|
hiddenLogLevels: [],
|
||||||
logsSortOrder: null,
|
logsSortOrder: null,
|
||||||
@ -166,6 +169,17 @@ export class UnthemedLogs extends PureComponent<Props, State> {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
onChangePrettifyLogMessage = (event?: React.SyntheticEvent) => {
|
||||||
|
const target = event && (event.target as HTMLInputElement);
|
||||||
|
if (target) {
|
||||||
|
const prettifyLogMessage = target.checked;
|
||||||
|
this.setState({
|
||||||
|
prettifyLogMessage,
|
||||||
|
});
|
||||||
|
store.set(SETTINGS_KEYS.prettifyLogMessage, prettifyLogMessage);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
onToggleLogLevel = (hiddenRawLevels: string[]) => {
|
onToggleLogLevel = (hiddenRawLevels: string[]) => {
|
||||||
const hiddenLogLevels = hiddenRawLevels.map((level) => LogLevel[level as LogLevel]);
|
const hiddenLogLevels = hiddenRawLevels.map((level) => LogLevel[level as LogLevel]);
|
||||||
this.setState({ hiddenLogLevels });
|
this.setState({ hiddenLogLevels });
|
||||||
@ -260,6 +274,7 @@ export class UnthemedLogs extends PureComponent<Props, State> {
|
|||||||
showLabels,
|
showLabels,
|
||||||
showTime,
|
showTime,
|
||||||
wrapLogMessage,
|
wrapLogMessage,
|
||||||
|
prettifyLogMessage,
|
||||||
dedupStrategy,
|
dedupStrategy,
|
||||||
hiddenLogLevels,
|
hiddenLogLevels,
|
||||||
logsSortOrder,
|
logsSortOrder,
|
||||||
@ -305,6 +320,9 @@ export class UnthemedLogs extends PureComponent<Props, State> {
|
|||||||
<InlineField label="Wrap lines" transparent>
|
<InlineField label="Wrap lines" transparent>
|
||||||
<InlineSwitch value={wrapLogMessage} onChange={this.onChangewrapLogMessage} transparent />
|
<InlineSwitch value={wrapLogMessage} onChange={this.onChangewrapLogMessage} transparent />
|
||||||
</InlineField>
|
</InlineField>
|
||||||
|
<InlineField label="Prettify JSON" transparent>
|
||||||
|
<InlineSwitch value={prettifyLogMessage} onChange={this.onChangePrettifyLogMessage} transparent />
|
||||||
|
</InlineField>
|
||||||
<InlineField label="Dedup" transparent>
|
<InlineField label="Dedup" transparent>
|
||||||
<RadioButtonGroup
|
<RadioButtonGroup
|
||||||
options={Object.keys(LogsDedupStrategy).map((dedupType: LogsDedupStrategy) => ({
|
options={Object.keys(LogsDedupStrategy).map((dedupType: LogsDedupStrategy) => ({
|
||||||
@ -356,6 +374,7 @@ export class UnthemedLogs extends PureComponent<Props, State> {
|
|||||||
enableLogDetails={true}
|
enableLogDetails={true}
|
||||||
forceEscape={forceEscape}
|
forceEscape={forceEscape}
|
||||||
wrapLogMessage={wrapLogMessage}
|
wrapLogMessage={wrapLogMessage}
|
||||||
|
prettifyLogMessage={prettifyLogMessage}
|
||||||
timeZone={timeZone}
|
timeZone={timeZone}
|
||||||
getFieldLinks={getFieldLinks}
|
getFieldLinks={getFieldLinks}
|
||||||
logsSortOrder={logsSortOrder}
|
logsSortOrder={logsSortOrder}
|
||||||
|
@ -12,7 +12,16 @@ interface LogsPanelProps extends PanelProps<Options> {}
|
|||||||
export const LogsPanel: React.FunctionComponent<LogsPanelProps> = ({
|
export const LogsPanel: React.FunctionComponent<LogsPanelProps> = ({
|
||||||
data,
|
data,
|
||||||
timeZone,
|
timeZone,
|
||||||
options: { showLabels, showTime, wrapLogMessage, showCommonLabels, sortOrder, dedupStrategy, enableLogDetails },
|
options: {
|
||||||
|
showLabels,
|
||||||
|
showTime,
|
||||||
|
wrapLogMessage,
|
||||||
|
showCommonLabels,
|
||||||
|
prettifyLogMessage,
|
||||||
|
sortOrder,
|
||||||
|
dedupStrategy,
|
||||||
|
enableLogDetails,
|
||||||
|
},
|
||||||
title,
|
title,
|
||||||
}) => {
|
}) => {
|
||||||
const style = useStyles2(getStyles(title));
|
const style = useStyles2(getStyles(title));
|
||||||
@ -57,6 +66,7 @@ export const LogsPanel: React.FunctionComponent<LogsPanelProps> = ({
|
|||||||
showLabels={showLabels}
|
showLabels={showLabels}
|
||||||
showTime={showTime}
|
showTime={showTime}
|
||||||
wrapLogMessage={wrapLogMessage}
|
wrapLogMessage={wrapLogMessage}
|
||||||
|
prettifyLogMessage={prettifyLogMessage}
|
||||||
timeZone={timeZone}
|
timeZone={timeZone}
|
||||||
getFieldLinks={getFieldLinks}
|
getFieldLinks={getFieldLinks}
|
||||||
logsSortOrder={sortOrder}
|
logsSortOrder={sortOrder}
|
||||||
|
@ -28,6 +28,12 @@ export const plugin = new PanelPlugin<Options>(LogsPanel).setPanelOptions((build
|
|||||||
description: '',
|
description: '',
|
||||||
defaultValue: false,
|
defaultValue: false,
|
||||||
})
|
})
|
||||||
|
.addBooleanSwitch({
|
||||||
|
path: 'prettifyLogMessage',
|
||||||
|
name: 'Prettify JSON',
|
||||||
|
description: '',
|
||||||
|
defaultValue: false,
|
||||||
|
})
|
||||||
.addBooleanSwitch({
|
.addBooleanSwitch({
|
||||||
path: 'enableLogDetails',
|
path: 'enableLogDetails',
|
||||||
name: 'Enable log details',
|
name: 'Enable log details',
|
||||||
|
@ -5,6 +5,7 @@ export interface Options {
|
|||||||
showCommonLabels: boolean;
|
showCommonLabels: boolean;
|
||||||
showTime: boolean;
|
showTime: boolean;
|
||||||
wrapLogMessage: boolean;
|
wrapLogMessage: boolean;
|
||||||
|
prettifyLogMessage: boolean;
|
||||||
enableLogDetails: boolean;
|
enableLogDetails: boolean;
|
||||||
sortOrder: LogsSortOrder;
|
sortOrder: LogsSortOrder;
|
||||||
dedupStrategy: LogsDedupStrategy;
|
dedupStrategy: LogsDedupStrategy;
|
||||||
|
Loading…
Reference in New Issue
Block a user