Skip to content

Commit

Permalink
Merge branch '7.8' into backport/7.8/pr-66015
Browse files Browse the repository at this point in the history
  • Loading branch information
elasticmachine authored May 12, 2020
2 parents 0b96b3c + 7b3fff1 commit b6e21af
Show file tree
Hide file tree
Showing 48 changed files with 572 additions and 212 deletions.
14 changes: 14 additions & 0 deletions docs/visualize/tsvb.asciidoc
Original file line number Diff line number Diff line change
Expand Up @@ -122,3 +122,17 @@ Edit the source for the Markdown visualization.
. To insert the mustache template variable into the editor, click the variable name.
+
The http://mustache.github.io/mustache.5.html[mustache syntax] uses the Handlebar.js processor, which is an extended version of the Mustache template language.

[float]
[[tsvb-style-markdown]]
==== Style Markdown text

Style your Markdown visualization using http://lesscss.org/features/[less syntax].

. Select *Markdown*.

. Select *Panel options*.

. Enter styling rules in *Custom CSS* section
+
Less in TSVB does not support custom plugins or inline JavaScript.
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -208,7 +208,7 @@
"leaflet-responsive-popup": "0.6.4",
"leaflet-vega": "^0.8.6",
"leaflet.heat": "0.2.0",
"less": "^2.7.3",
"less": "npm:@elastic/less@2.7.3-kibana",
"less-loader": "5.0.0",
"lodash": "npm:@elastic/[email protected]",
"lodash.clonedeep": "^4.5.0",
Expand Down
4 changes: 4 additions & 0 deletions packages/kbn-es/src/utils/native_realm.js
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,10 @@ exports.NativeRealm = class NativeRealm {
}

const reservedUsers = await this.getReservedUsers();
if (!reservedUsers || reservedUsers.length < 1) {
throw new Error('no reserved users found, unable to set native realm passwords');
}

await Promise.all(
reservedUsers.map(async user => {
await this.setPassword(user, options[`password.${user}`]);
Expand Down
5 changes: 4 additions & 1 deletion src/plugins/console/public/styles/_app.scss
Original file line number Diff line number Diff line change
@@ -1,8 +1,11 @@
// TODO: Move all of the styles here (should be modularised by, e.g., CSS-in-JS or CSS modules).
@import '@elastic/eui/src/components/header/variables';

// This value is calculated to static value using SCSS because calc in calc has issues in IE11
$headerHeightOffset: $euiHeaderHeightCompensation * 2;

#consoleRoot {
height: calc(100vh - calc(#{$euiHeaderChildSize} * 2));
height: calc(100vh - #{$headerHeightOffset});
display: flex;
flex: 1 1 auto;
// Make sure the editor actions don't create scrollbars on this container
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ class MarkdownPanelConfigUi extends Component {
const lessSrc = `#markdown-${model.id} {
${value}
}`;
lessC.render(lessSrc, { compress: true }, (e, output) => {
lessC.render(lessSrc, { compress: true, javascriptEnabled: false }, (e, output) => {
const parts = { markdown_less: value };
if (output) {
parts.markdown_css = output.css;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,8 @@ export const getSeverityColor = (nodeSeverity: string) => {
switch (nodeSeverity) {
case severity.warning:
return theme.euiColorVis0;
case severity.minor || severity.major:
case severity.minor:
case severity.major:
return theme.euiColorVis5;
case severity.critical:
return theme.euiColorVis9;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,33 +30,30 @@ export const DrilldownHelloBar: React.FC<DrilldownHelloBarProps> = ({
onHideClick = () => {},
}) => {
return (
<EuiCallOut
data-test-subj={WELCOME_MESSAGE_TEST_SUBJ}
title={
<EuiFlexGroup className="drdHelloBar__content">
<EuiFlexItem grow={false}>
<div style={{ marginLeft: '8px' }}>
<EuiIcon type="help" />
</div>
</EuiFlexItem>
<EuiFlexItem grow={true}>
<EuiText size={'s'}>
<EuiTextColor color="subdued">{txtHelpText}</EuiTextColor>
</EuiText>
{docsLink && (
<>
<EuiSpacer size={'xs'} />
<EuiLink href={docsLink}>{txtViewDocsLinkLabel}</EuiLink>
</>
)}
</EuiFlexItem>
<EuiFlexItem grow={false}>
<EuiButtonEmpty size="xs" onClick={onHideClick}>
{txtHideHelpButtonLabel}
</EuiButtonEmpty>
</EuiFlexItem>
</EuiFlexGroup>
}
/>
<EuiCallOut data-test-subj={WELCOME_MESSAGE_TEST_SUBJ}>
<EuiFlexGroup>
<EuiFlexItem grow={false}>
<div style={{ marginLeft: '8px' }}>
<EuiIcon type="help" />
</div>
</EuiFlexItem>
<EuiFlexItem grow={1}>
<EuiText size={'s'}>
<EuiTextColor color="subdued">{txtHelpText}</EuiTextColor>
</EuiText>
{docsLink && (
<>
<EuiSpacer size={'xs'} />
<EuiLink href={docsLink}>{txtViewDocsLinkLabel}</EuiLink>
</>
)}
</EuiFlexItem>
<EuiFlexItem grow={false}>
<EuiButtonEmpty size="xs" onClick={onHideClick}>
{txtHideHelpButtonLabel}
</EuiButtonEmpty>
</EuiFlexItem>
</EuiFlexGroup>
</EuiCallOut>
);
};
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ export const Expressions: React.FC<Props> = props => {
fetch: alertsContext.http.fetch,
toastWarning: alertsContext.toastNotifications.addWarning,
});

const [timeSize, setTimeSize] = useState<number | undefined>(1);
const [timeUnit, setTimeUnit] = useState<TimeUnit>('m');
const derivedIndexPattern = useMemo(() => createDerivedIndexPattern('metrics'), [
Expand Down Expand Up @@ -166,52 +167,57 @@ export const Expressions: React.FC<Props> = props => {
[alertParams.criteria, setAlertParams]
);

useEffect(() => {
const preFillAlertCriteria = useCallback(() => {
const md = alertsContext.metadata;
if (md) {
if (md.currentOptions?.metrics) {
setAlertParams(
'criteria',
md.currentOptions.metrics.map(metric => ({
metric: metric.field,
comparator: Comparator.GT,
threshold: [],
timeSize,
timeUnit,
aggType: metric.aggregation,
}))
);
} else {
setAlertParams('criteria', [defaultExpression]);
}
if (md && md.currentOptions?.metrics) {
setAlertParams(
'criteria',
md.currentOptions.metrics.map(metric => ({
metric: metric.field,
comparator: Comparator.GT,
threshold: [],
timeSize,
timeUnit,
aggType: metric.aggregation,
}))
);
} else {
setAlertParams('criteria', [defaultExpression]);
}
}, [alertsContext.metadata, setAlertParams, timeSize, timeUnit]);

if (md.currentOptions) {
if (md.currentOptions.filterQuery) {
setAlertParams('filterQueryText', md.currentOptions.filterQuery);
setAlertParams(
'filterQuery',
convertKueryToElasticSearchQuery(md.currentOptions.filterQuery, derivedIndexPattern) ||
''
);
} else if (md.currentOptions.groupBy && md.series) {
const filter = `${md.currentOptions.groupBy}: "${md.series.id}"`;
setAlertParams('filterQueryText', filter);
setAlertParams(
'filterQuery',
convertKueryToElasticSearchQuery(filter, derivedIndexPattern) || ''
);
}
const preFillAlertFilter = useCallback(() => {
const md = alertsContext.metadata;
if (md && md.currentOptions?.filterQuery) {
setAlertParams('filterQueryText', md.currentOptions.filterQuery);
setAlertParams(
'filterQuery',
convertKueryToElasticSearchQuery(md.currentOptions.filterQuery, derivedIndexPattern) || ''
);
} else if (md && md.currentOptions?.groupBy && md.series) {
const filter = `${md.currentOptions?.groupBy}: "${md.series.id}"`;
setAlertParams('filterQueryText', filter);
setAlertParams(
'filterQuery',
convertKueryToElasticSearchQuery(filter, derivedIndexPattern) || ''
);
}
}, [alertsContext.metadata, derivedIndexPattern, setAlertParams]);

setAlertParams('groupBy', md.currentOptions.groupBy);
}
setAlertParams('sourceId', source?.id);
useEffect(() => {
if (alertParams.criteria && alertParams.criteria.length) {
setTimeSize(alertParams.criteria[0].timeSize);
setTimeUnit(alertParams.criteria[0].timeUnit);
} else {
if (!alertParams.criteria) {
setAlertParams('criteria', [defaultExpression]);
}
if (!alertParams.sourceId) {
setAlertParams('sourceId', source?.id || 'default');
}
preFillAlertCriteria();
}

if (!alertParams.filterQuery) {
preFillAlertFilter();
}

if (!alertParams.sourceId) {
setAlertParams('sourceId', source?.id || 'default');
}
}, [alertsContext.metadata, defaultExpression, source]); // eslint-disable-line react-hooks/exhaustive-deps

Expand Down
5 changes: 5 additions & 0 deletions x-pack/plugins/infra/server/lib/alerting/common/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,11 @@ export const oneOfLiterals = (arrayOfLiterals: Readonly<string[]>) =>
});

export const validateIsStringElasticsearchJSONFilter = (value: string) => {
if (value === '') {
// Allow clearing the filter.
return;
}

const errorMessage = 'filterQuery must be a valid Elasticsearch filter expressed in JSON';
try {
const parsedValue = JSON.parse(value);
Expand Down
2 changes: 2 additions & 0 deletions x-pack/plugins/ml/common/util/job_utils.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@ export function mlFunctionToESAggregation(functionName: string): string | null;

export function isModelPlotEnabled(job: Job, detectorIndex: number, entityFields: any[]): boolean;

export function isModelPlotChartableForDetector(job: Job, detectorIndex: number): boolean;

export function getSafeAggregationName(fieldName: string, index: number): string;

export function getLatestDataOrBucketTimestamp(
Expand Down
22 changes: 12 additions & 10 deletions x-pack/plugins/ml/common/util/job_utils.js
Original file line number Diff line number Diff line change
Expand Up @@ -105,18 +105,20 @@ export function isModelPlotChartableForDetector(job, detectorIndex) {
const dtr = dtrs[detectorIndex];
const functionName = dtr.function;

// Model plot can be charted for any of the functions which map to ES aggregations,
// Model plot can be charted for any of the functions which map to ES aggregations
// (except rare, for which no model plot results are generated),
// plus varp and info_content functions.
isModelPlotChartable =
mlFunctionToESAggregation(functionName) !== null ||
[
'varp',
'high_varp',
'low_varp',
'info_content',
'high_info_content',
'low_info_content',
].includes(functionName) === true;
functionName !== 'rare' &&
(mlFunctionToESAggregation(functionName) !== null ||
[
'varp',
'high_varp',
'low_varp',
'info_content',
'high_info_content',
'low_info_content',
].includes(functionName) === true);
}

return isModelPlotChartable;
Expand Down
13 changes: 12 additions & 1 deletion x-pack/plugins/ml/common/util/job_utils.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -307,7 +307,14 @@ describe('ML - job utils', () => {

const job2 = {
analysis_config: {
detectors: [{ function: 'count' }, { function: 'info_content' }],
detectors: [
{ function: 'count' },
{ function: 'info_content' },
{
function: 'rare',
by_field_name: 'mlcategory',
},
],
},
model_plot_config: {
enabled: true,
Expand All @@ -325,6 +332,10 @@ describe('ML - job utils', () => {
test('returns true for info_content detector when model plot is enabled', () => {
expect(isModelPlotChartableForDetector(job2, 1)).toBe(true);
});

test('returns false for rare by mlcategory when model plot is enabled', () => {
expect(isModelPlotChartableForDetector(job2, 2)).toBe(false);
});
});

describe('getPartitioningFieldNames', () => {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ import { chartLimits, getChartType } from '../../util/chart_utils';
import { getEntityFieldList } from '../../../../common/util/anomaly_utils';
import {
isSourceDataChartableForDetector,
isModelPlotChartableForDetector,
isModelPlotEnabled,
} from '../../../../common/util/job_utils';
import { mlResultsService } from '../../services/results_service';
Expand Down Expand Up @@ -420,7 +421,7 @@ function processRecordsForDisplay(anomalyRecords) {
// is chartable, and if model plot is enabled for the job.
const job = mlJobService.getJob(record.job_id);
let isChartable = isSourceDataChartableForDetector(job, record.detector_index);
if (isChartable === false) {
if (isChartable === false && isModelPlotChartableForDetector(job, record.detector_index)) {
// Check if model plot is enabled for this job.
// Need to check the entity fields for the record in case the model plot config has a terms list.
const entityFields = getEntityFieldList(record);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ import {
import { getEntityFieldList } from '../../../common/util/anomaly_utils';
import {
isSourceDataChartableForDetector,
isModelPlotChartableForDetector,
isModelPlotEnabled,
} from '../../../common/util/job_utils';
import { parseInterval } from '../../../common/util/parse_interval';
Expand Down Expand Up @@ -636,7 +637,10 @@ export async function loadAnomaliesTableData(
// TODO - when job_service is moved server_side, move this to server endpoint.
const job = mlJobService.getJob(jobId);
let isChartable = isSourceDataChartableForDetector(job, anomaly.detectorIndex);
if (isChartable === false) {
if (
isChartable === false &&
isModelPlotChartableForDetector(job, anomaly.detectorIndex)
) {
// Check if model plot is enabled for this job.
// Need to check the entity fields for the record in case the model plot config has a terms list.
// If terms is specified, model plot is only stored if both the partition and by fields appear in the list.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,10 @@ import _ from 'lodash';
import { Observable } from 'rxjs';
import { map } from 'rxjs/operators';
import { ml } from '../services/ml_api_service';
import { isModelPlotEnabled } from '../../../common/util/job_utils';
import {
isModelPlotChartableForDetector,
isModelPlotEnabled,
} from '../../../common/util/job_utils';
// @ts-ignore
import { buildConfigFromDetector } from '../util/chart_config_builder';
import { mlResultsService } from '../services/results_service';
Expand All @@ -24,7 +27,10 @@ function getMetricData(
latestMs: number,
interval: string
): Observable<ModelPlotOutput> {
if (isModelPlotEnabled(job, detectorIndex, entityFields)) {
if (
isModelPlotChartableForDetector(job, detectorIndex) &&
isModelPlotEnabled(job, detectorIndex, entityFields)
) {
// Extract the partition, by, over fields on which to filter.
const criteriaFields = [];
const detector = job.analysis_config.detectors[detectorIndex];
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ import { ResizeChecker } from '../../../../../../src/plugins/kibana_utils/public
import { ANOMALIES_TABLE_DEFAULT_QUERY_SIZE } from '../../../common/constants/search';
import {
isModelPlotEnabled,
isModelPlotChartableForDetector,
isSourceDataChartableForDetector,
isTimeSeriesViewDetector,
mlFunctionToESAggregation,
Expand Down Expand Up @@ -506,11 +507,9 @@ export class TimeSeriesExplorer extends React.Component {
contextForecastData: undefined,
focusChartData: undefined,
focusForecastData: undefined,
modelPlotEnabled: isModelPlotEnabled(
currentSelectedJob,
selectedDetectorIndex,
entityControls
),
modelPlotEnabled:
isModelPlotChartableForDetector(currentSelectedJob, selectedDetectorIndex) &&
isModelPlotEnabled(currentSelectedJob, selectedDetectorIndex, entityControls),
hasResults: false,
dataNotChartable: false,
}
Expand Down
Loading

0 comments on commit b6e21af

Please sign in to comment.